Compare commits

...

46 Commits

Author SHA1 Message Date
nightpool 40bd7a4282 don't send spammy mentions 2019-06-15 13:05:28 -04:00
nightpool c296d35be4 show warning message for locked account 2019-06-15 13:05:28 -04:00
nightpool 1a6bdd61e9 Use git commit hash as part of the cache key
avoids issues with model caching being incompatible across versions
2019-06-15 13:03:40 -04:00
khr 2b52b458e6 Restore timeline 2019-05-22 18:53:04 -07:00
khr 6fe1660669 Remove extra stats block 2019-05-22 18:16:08 -07:00
khr 5610587046 Query 2019-05-22 16:55:29 -07:00
khr bfef28dd9f Merge branch 'theme_light' into cybrespace 2019-05-22 16:50:23 -07:00
nightpool 600c7b2377 fix full-width embeds and light theme embeds 2019-05-22 16:50:14 -07:00
khr a8284b65aa Merge branch 'theme_win95' into cybrespace 2019-05-22 16:48:41 -07:00
khr 8da4fc973b Merge branch 'theme_light' into cybrespace 2019-05-22 16:47:30 -07:00
khr fe2b7be467 Merge branch 'theme_cybre' into cybrespace 2019-05-22 16:46:56 -07:00
khr 063b2e2b2d Merge branch 'theme_base' into cybrespace 2019-05-22 16:46:52 -07:00
khr 1875aa0946 Merge branches 'dependency_whatinput', 'feature_512_char_toots', 'feature_cybrespace_locale', 'feature_disable_reply_counts', 'feature_hotlink_twitter_mentions', 'feature_longer_bios' and 'feature_machine_registration_task' into cybrespace 2019-05-22 16:46:43 -07:00
khr ac21ecade8 Windows 95 theme 2019-05-22 16:43:36 -07:00
khr e848f34584 Poll support 2019-05-22 16:26:44 -07:00
khr 59c00e0ba4 Cybrespace light theme 2019-05-22 16:21:56 -07:00
nightpool d74455b0aa remove duplicate border radi 2019-05-22 16:19:09 -07:00
khr 7a141e6522 fix full-width embeds 2019-05-22 16:18:47 -07:00
khr 57560336d7 Cybrespace theme (dark) 2019-05-22 16:14:09 -07:00
khr d3de5513c8 Use lighter text for show thread link 2019-05-22 16:05:12 -07:00
khr d902bbab25 Fix unnecessary scrollbar on compose drawer 2019-05-22 16:05:11 -07:00
khr 739e64d2a9 Fix media height weirdness, handle new status cards 2019-05-22 16:05:11 -07:00
chr f38a43506c Base SCSS for cybrespace themes
Performs some baseline tweaks to the mastodon application scss that are
shared between all the cybrespace themes
2019-05-22 16:05:11 -07:00
Andrew 338b03bdfe Feature: add a rake task that's like register but also accepts password
and produces cleaner output
2019-05-22 16:04:48 -07:00
khr 9cd0511ba9 Bio length -> 413 characters
Increase the cybre.space profile bio text length limit to 413
characters. Also modifies the account settings page to automatically
resize the textbox to the size of the contained text, so that it's
easier to type longer bios.
2019-05-22 16:03:42 -07:00
Andrew ba09c275dd Hotlink twitter mentions
Differentiate twitter mentions from normal mentions
2019-05-22 16:03:09 -07:00
Andrew b1f762fffe Remove reply counts on non-expanded view 2019-05-22 16:00:34 -07:00
khr ab4353082e Cybrespace locale
An alternative locale that replaces "toot" with "ping", "favorite" with
"florp", and "boost" with "relay", as well as a few other miscellaneous
changes. Also includes alternate settings that make the en-CY locale
default instead of en-US, and fixes the timestamps.
2019-05-22 15:59:05 -07:00
Andrew 3b389dbc50 Feature: 512-character limit in the toot box on client and serverside 2019-05-22 15:54:35 -07:00
Andrew 3dbf9e8a34 Add whatinput dependency for more responsive focus styling 2019-05-22 15:47:16 -07:00
khr 555013b54d Restore 2.7 landing page 2019-05-22 15:45:17 -07:00
khr 610871c82d Cybrespace branding changes 2019-05-22 14:48:26 -07:00
Eugen Rochko 370ec7e771 Bump version to 2.8.3 2019-05-19 22:35:49 +02:00
ThibG 9222c26e19 Fix “invited by” not showing up for invited accounts in admin interface (#10791) 2019-05-19 22:32:25 +02:00
Hinaloe 94439a1da7 fix `isSubmitting` prop case (#10785) 2019-05-19 22:32:14 +02:00
ThibG a6815a7578 Add post-deployment migration script to delete public-boosts-of-private-toots (#10783) 2019-05-19 16:27:11 +02:00
Ben Lubar d587a943a5 add og:image:alt for media attachments in embeds (#10779) 2019-05-19 16:26:00 +02:00
ThibG 3c27687a6e Prevent from publicly boosting one's own private toots (#10775) 2019-05-19 16:25:40 +02:00
ThibG ee17d81b8a Minor performance improvements and cleanup in formatter (#10765) 2019-05-19 16:25:39 +02:00
Neil Moore 9e95af3391 Adds click-able div that expands status (#10733) (#10766)
The clickable div is positioned under the account avatar and covers
all empty space below it to the end of the status.
2019-05-19 16:25:20 +02:00
nzws 91e25a20ce Fix some colors in light theme (#10754)
* Fix typo in light theme

* Fix background color of empty column
2019-05-19 16:25:20 +02:00
ThibG 47e0928c5b Change icon and label depending on whether media is marked as sensitive (#10748)
* Change icon and label depending on whether media is marked as sensitive

* WiP use a checkbox
2019-05-19 16:25:20 +02:00
Maciek Baron c407a4edf8 Improve poll link accessibility (#10720)
* Add distinction between hover and active/focus states
* Resolves #10198
2019-05-19 16:25:20 +02:00
Jeong Arm 7a6464bea0 Bring back crossed eye icon on gallery (#10715) 2019-05-19 16:25:20 +02:00
nzws 9679ec4fcb Fix some colors of high contrast theme (#10711)
* Fix "nothing here" text color of high contrast

* Fix counter border color of high contrast
2019-05-19 16:25:20 +02:00
ThibG b40dfc124b Add description on hover in media gallery (#10713) 2019-05-19 16:25:20 +02:00
123 changed files with 6578 additions and 382 deletions

View File

@ -3,6 +3,28 @@ Changelog
All notable changes to this project will be documented in this file.
## [2.8.3] - 2019-05-19
### Added
- Add `og:image:alt` OpenGraph tag ([BenLubar](https://github.com/tootsuite/mastodon/pull/10779))
- Add clickable area below avatar in statuses in web UI ([Dar13](https://github.com/tootsuite/mastodon/pull/10766))
- Add crossed-out eye icon on account gallery in web UI ([Kjwon15](https://github.com/tootsuite/mastodon/pull/10715))
- Add media description tooltip to thumbnails in web UI ([ThibG](https://github.com/tootsuite/mastodon/pull/10713))
### Changed
- Change "mark as sensitive" button into a checkbox for clarity ([ThibG](https://github.com/tootsuite/mastodon/pull/10748))
### Fixed
- Fix bug allowing users to publicly boost their private statuses ([ThibG](https://github.com/tootsuite/mastodon/pull/10775), [ThibG](https://github.com/tootsuite/mastodon/pull/10783))
- Fix performance in formatter by a little ([ThibG](https://github.com/tootsuite/mastodon/pull/10765))
- Fix some colors in the light theme ([yuzulabo](https://github.com/tootsuite/mastodon/pull/10754))
- Fix some colors of the high contrast theme ([yuzulabo](https://github.com/tootsuite/mastodon/pull/10711))
- Fix ambivalent active state of poll refresh button in web UI ([MaciekBaron](https://github.com/tootsuite/mastodon/pull/10720))
- Fix duplicate posting being possible from web UI ([hinaloe](https://github.com/tootsuite/mastodon/pull/10785))
- Fix "invited by" not showing up in admin UI ([ThibG](https://github.com/tootsuite/mastodon/pull/10791))
## [2.8.2] - 2019-05-05
### Added

View File

@ -6,6 +6,8 @@ class AboutController < ApplicationController
before_action :set_instance_presenter, only: [:show, :more, :terms]
def show
serializable_resource = ActiveModelSerializers::SerializableResource.new(InitialStatePresenter.new(initial_state_params), serializer: InitialStateSerializer)
@initial_state_json = serializable_resource.to_json
@hide_navbar = true
end
@ -27,4 +29,11 @@ class AboutController < ApplicationController
def set_instance_presenter
@instance_presenter = InstancePresenter.new
end
def initial_state_params
{
settings: { known_fediverse: Setting.show_known_fediverse_at_about_page },
token: current_session&.token,
}
end
end

View File

@ -20,7 +20,12 @@ module Localized
if ENV['DEFAULT_LOCALE'].present?
I18n.default_locale
else
request_locale || I18n.default_locale
case request_locale
when /en\b/, nil
I18n.default_locale
else
request_locale
end
end
end

View File

@ -3,6 +3,7 @@
module SettingsHelper
HUMAN_LOCALES = {
en: 'English',
'en-CY': 'English (Cybre)',
ar: 'العربية',
ast: 'Asturianu',
bg: 'Български',

Binary file not shown.

Binary file not shown.

After

Width:  |  Height:  |  Size: 622 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 223 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 232 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 378 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 34 KiB

After

Width:  |  Height:  |  Size: 40 KiB

View File

@ -0,0 +1,64 @@
<svg xmlns="http://www.w3.org/2000/svg" width="384" version="1.1" height="384">
<g transform="translate(-282.71845,-76)" id="RenderLayer_LineSet">
<g id="strokes">
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path2" d="m 405.991,306.829 v 10 10 10 10 10 10 10 10 6.581 5.978 9.656 3.057" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path4" d="m 405.991,409.044 v 0 -9.656 -5.978 -10 -10 -10 -10 -10 -10 -10 -10 -6.581" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path6" d="m 370.692,127.899 v 1.329 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path8" d="m 439.906,283.073 v 0 h -10 -10 -10.303 -3.612 -10 -10 -10 -2.337 l -2.962,-2.901 v 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path10" d="m 373.654,283.073 -2.962,-2.901 v -10 -10 -10 -10 -10 -10 -1.283 -10 -10 -10 -10 -10 -9.658" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path12" d="m 370.692,127.899 h -7.383 -10 -2.899 -5.311 v 0 l -0.45,0.28 -0.37,0.387 -0.268,0.47 v 0.192 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 2.901 10 4.487 5.906 3.363 10 10 10 10 10 10 10 10 6.581 l 6.235,6.039 7.183,6.957 2.643,2.56 3.237,3.135 v 0 h 7.383 2.962 10 10 10 2.337 v 0 0 -3.057" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path14" d="m 584.095,303.466 3.074,3.363 v 10 10 10 10 10 10 10 10 6.581 6.183 9.988 10e-4 0.001 2.518 h 6.497 10 2.976 7.534 v 0 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path16" d="m 615.989,393.41 v -10 -10 -10 -10 -10 -10 -10 -10 -6.581 -3.363 -5.906 -10 -4.487 -2.901 -10 -10 -10 -10 -10 -10 -1.283 -10 -10 -10 -10 -10 -9.658 -2.701 -4.955 -10 -0.947 -10 -1.4 -0.061 l -0.299,-0.524 -0.394,-0.413 -0.019,-0.019 v 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path18" d="m 584.093,129.228 h -10 -10 -10 -10 l -10,-0.001 h -10 -5.476 -10 -10 -10 -10 -10 -10 l -10,-0.001 h -8.828 -10 -10 -10 -0.326 -3.615 l -10,0.001 h -10 l -10,0.001 h -2.205 -2.951 v 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path20" d="m 615.277,128.211 v 0 l -0.501,-0.312 v 0 0 h -8.134 -10 -2.976 -6.497 v 1.329" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path22" d="m 615.69,128.643 0.299,0.524 v 0.061 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 2.901 10 4.487 5.906 3.363 10 10 10 10 10 10 10 10 6.581 6.183 9.987 0.626 l -0.447,0.784 -0.617,0.644 -0.749,0.467" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path24" d="m 587.169,156.53 v 0 0 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 l -3.074,2.901 h -10 -10 -10 -10 -10 -10 -5.424" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path26" d="m 370.692,129.228 v -1.329 0 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path28" d="m 584.093,129.228 h 3.076" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path30" d="m 350.41,140.628 h 10 2.899 v 10 0.947 h -3.555 -9.344 v 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path32" d="m 587.169,129.228 v 10 1.4 10 0.947 4.955" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path34" d="m 350.41,151.575 v -10 -0.947" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path36" d="m 593.666,151.575 v -10 -0.947 0 h 10 2.976" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path38" d="m 606.642,140.628 v 10 0.947 h -10 -2.976 v 0 -10 -0.947" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path40" d="m 615.69,128.643 -0.394,-0.413 -0.019,-0.019 v 0 l -0.501,-0.312" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path42" d="m 615.989,393.41 v 6.183 9.987 0.626 l -0.447,0.783 -0.576,0.603 -0.041,0.042 v 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path44" d="m 614.925,411.634 v 0 l -0.749,0.467" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path46" d="m 615.69,128.643 -0.009,-0.01 -0.404,-0.422 -0.501,-0.312" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path48" d="m 614.176,412.101 0.749,-0.467 v 0 l 0.041,-0.042 0.576,-0.603 0.447,-0.783 v -0.626 -9.987 -6.183" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path50" d="m 406.223,306.613 -0.232,0.216 v 0 l 0.232,-0.216 3.38,-3.147 h 10 10 10.303 10 10 10 10 10 10 10 8.765 10 10 1.007" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path52" d="m 518.671,283.073 v 0 h -10 -2.247" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path54" d="m 615.277,128.211 0.404,0.422" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path56" d="m 383.445,273.927 h 10 10 10 10 10 6.461" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path58" d="m 576.555,273.927 2.03,-0.051 1.978,-0.302 1.707,-0.727" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path60" d="m 582.27,272.847 1.099,-1.131 0.456,-1.309 0.077,-1.342" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path62" d="m 583.902,269.065 v -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -9.834 0 -10 -7.959" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path64" d="m 583.902,141.272 -0.077,-1.344 -0.457,-1.309 -1.098,-1.13" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path66" d="m 582.27,137.489 -1.709,-0.727 -1.977,-0.301 -2.029,-0.051" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path68" d="m 576.555,136.41 h -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -3.11 l -2.03,0.051 -1.978,0.302 -1.707,0.726" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path70" d="m 377.73,137.489 -1.099,1.131 -0.456,1.309 -0.077,1.343" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path72" d="m 376.098,269.065 0.077,1.343 0.457,1.309 1.098,1.13" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path74" d="m 377.73,272.847 1.709,0.727 1.977,0.302 2.029,0.051" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path76" d="m 457.882,318.176 v 10 10 10 10 10 10 10 8.996 l -0.375,1.491 -0.542,1.03" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path78" d="m 456.965,399.693 h -10 -10 -8.726 l -0.542,-1.03 -0.375,-1.491" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path80" d="m 539.678,303.466 -0.064,-0.035 h -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10.198 l -1.889,1.029 -1.304,1.491" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path82" d="m 543.74,411.917 v -2.465 -0.024 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -2.742 l -1.686,-1.925 -2.376,-1.295" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path84" d="m 427.612,316.452 0.42,-0.797 h 10 10 8.933 l 0.542,1.03 0.375,1.491" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path86" d="m 427.322,317.607 0.29,-1.155" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path88" d="m 350.41,151.575 v -10 -0.947" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path90" d="m 370.692,127.899 v 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path92" d="m 376.098,141.272 v 10 7.954 0.005 10 10 10 10 10 10 10 10 10 10 9.834" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path94" d="m 405.991,409.044 v 3.057" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path96" d="m 406.223,305.951 v 0.662 0 0 0 10 10 10 10 10 10 10 10 10 10 2.333 0.098 2.873" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path98" d="m 427.322,397.172 v -10 -10 -10 -10 -10 -10 -10 -9.565" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path100" d="m 405.991,409.044 h 0.232" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path102" d="m 506.424,283.073 h -3.436 -10 -10 -10 -10 -6.548 -3.543 -10e-4 -10 -2.99" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path104" d="m 406.223,411.917 h 10 10 10 10 10 10 10 10 10 10 10 10 10 7.517" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path106" d="m 518.671,273.927 h 10 10 10 10 10 7.884" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path108" d="m 439.906,273.927 h 6.803 v 0 h 2.704 10 10 10 10 10 10.551 2.65 10e-4 6.056" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path110" d="m 539.678,303.466 h 10 10 10 10 4.417" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path112" d="m 587.169,156.53 v 0" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path114" d="m 543.74,409.452 10,0.029 10,0.03 10,0.03 9.999,0.029 3.43,0.01" />
<path style="fill:none;stroke:#87B97D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path116" d="m 615.989,393.41 v -10 -10 -10 -10 -10 -10 -10 -10 -6.581" />
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 12 KiB

View File

@ -0,0 +1,64 @@
<svg xmlns="http://www.w3.org/2000/svg" width="384" version="1.1" height="384">
<g transform="translate(-282.71845,-76)" id="RenderLayer_LineSet">
<g id="strokes">
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path2" d="m 405.991,306.829 v 10 10 10 10 10 10 10 10 6.581 5.978 9.656 3.057" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path4" d="m 405.991,409.044 v 0 -9.656 -5.978 -10 -10 -10 -10 -10 -10 -10 -10 -6.581" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path6" d="m 370.692,127.899 v 1.329 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path8" d="m 439.906,283.073 v 0 h -10 -10 -10.303 -3.612 -10 -10 -10 -2.337 l -2.962,-2.901 v 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path10" d="m 373.654,283.073 -2.962,-2.901 v -10 -10 -10 -10 -10 -10 -1.283 -10 -10 -10 -10 -10 -9.658" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path12" d="m 370.692,127.899 h -7.383 -10 -2.899 -5.311 v 0 l -0.45,0.28 -0.37,0.387 -0.268,0.47 v 0.192 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 2.901 10 4.487 5.906 3.363 10 10 10 10 10 10 10 10 6.581 l 6.235,6.039 7.183,6.957 2.643,2.56 3.237,3.135 v 0 h 7.383 2.962 10 10 10 2.337 v 0 0 -3.057" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path14" d="m 584.095,303.466 3.074,3.363 v 10 10 10 10 10 10 10 10 6.581 6.183 9.988 10e-4 0.001 2.518 h 6.497 10 2.976 7.534 v 0 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path16" d="m 615.989,393.41 v -10 -10 -10 -10 -10 -10 -10 -10 -6.581 -3.363 -5.906 -10 -4.487 -2.901 -10 -10 -10 -10 -10 -10 -1.283 -10 -10 -10 -10 -10 -9.658 -2.701 -4.955 -10 -0.947 -10 -1.4 -0.061 l -0.299,-0.524 -0.394,-0.413 -0.019,-0.019 v 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path18" d="m 584.093,129.228 h -10 -10 -10 -10 l -10,-0.001 h -10 -5.476 -10 -10 -10 -10 -10 -10 l -10,-0.001 h -8.828 -10 -10 -10 -0.326 -3.615 l -10,0.001 h -10 l -10,0.001 h -2.205 -2.951 v 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path20" d="m 615.277,128.211 v 0 l -0.501,-0.312 v 0 0 h -8.134 -10 -2.976 -6.497 v 1.329" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path22" d="m 615.69,128.643 0.299,0.524 v 0.061 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 2.901 10 4.487 5.906 3.363 10 10 10 10 10 10 10 10 6.581 6.183 9.987 0.626 l -0.447,0.784 -0.617,0.644 -0.749,0.467" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path24" d="m 587.169,156.53 v 0 0 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 l -3.074,2.901 h -10 -10 -10 -10 -10 -10 -5.424" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path26" d="m 370.692,129.228 v -1.329 0 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path28" d="m 584.093,129.228 h 3.076" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path30" d="m 350.41,140.628 h 10 2.899 v 10 0.947 h -3.555 -9.344 v 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path32" d="m 587.169,129.228 v 10 1.4 10 0.947 4.955" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path34" d="m 350.41,151.575 v -10 -0.947" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path36" d="m 593.666,151.575 v -10 -0.947 0 h 10 2.976" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path38" d="m 606.642,140.628 v 10 0.947 h -10 -2.976 v 0 -10 -0.947" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path40" d="m 615.69,128.643 -0.394,-0.413 -0.019,-0.019 v 0 l -0.501,-0.312" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path42" d="m 615.989,393.41 v 6.183 9.987 0.626 l -0.447,0.783 -0.576,0.603 -0.041,0.042 v 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path44" d="m 614.925,411.634 v 0 l -0.749,0.467" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path46" d="m 615.69,128.643 -0.009,-0.01 -0.404,-0.422 -0.501,-0.312" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path48" d="m 614.176,412.101 0.749,-0.467 v 0 l 0.041,-0.042 0.576,-0.603 0.447,-0.783 v -0.626 -9.987 -6.183" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path50" d="m 406.223,306.613 -0.232,0.216 v 0 l 0.232,-0.216 3.38,-3.147 h 10 10 10.303 10 10 10 10 10 10 10 8.765 10 10 1.007" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path52" d="m 518.671,283.073 v 0 h -10 -2.247" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path54" d="m 615.277,128.211 0.404,0.422" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path56" d="m 383.445,273.927 h 10 10 10 10 10 6.461" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path58" d="m 576.555,273.927 2.03,-0.051 1.978,-0.302 1.707,-0.727" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path60" d="m 582.27,272.847 1.099,-1.131 0.456,-1.309 0.077,-1.342" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path62" d="m 583.902,269.065 v -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -9.834 0 -10 -7.959" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path64" d="m 583.902,141.272 -0.077,-1.344 -0.457,-1.309 -1.098,-1.13" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path66" d="m 582.27,137.489 -1.709,-0.727 -1.977,-0.301 -2.029,-0.051" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path68" d="m 576.555,136.41 h -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -3.11 l -2.03,0.051 -1.978,0.302 -1.707,0.726" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path70" d="m 377.73,137.489 -1.099,1.131 -0.456,1.309 -0.077,1.343" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path72" d="m 376.098,269.065 0.077,1.343 0.457,1.309 1.098,1.13" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path74" d="m 377.73,272.847 1.709,0.727 1.977,0.302 2.029,0.051" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path76" d="m 457.882,318.176 v 10 10 10 10 10 10 10 8.996 l -0.375,1.491 -0.542,1.03" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path78" d="m 456.965,399.693 h -10 -10 -8.726 l -0.542,-1.03 -0.375,-1.491" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path80" d="m 539.678,303.466 -0.064,-0.035 h -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10.198 l -1.889,1.029 -1.304,1.491" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path82" d="m 543.74,411.917 v -2.465 -0.024 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -2.742 l -1.686,-1.925 -2.376,-1.295" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path84" d="m 427.612,316.452 0.42,-0.797 h 10 10 8.933 l 0.542,1.03 0.375,1.491" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path86" d="m 427.322,317.607 0.29,-1.155" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path88" d="m 350.41,151.575 v -10 -0.947" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path90" d="m 370.692,127.899 v 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path92" d="m 376.098,141.272 v 10 7.954 0.005 10 10 10 10 10 10 10 10 10 10 9.834" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path94" d="m 405.991,409.044 v 3.057" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path96" d="m 406.223,305.951 v 0.662 0 0 0 10 10 10 10 10 10 10 10 10 10 2.333 0.098 2.873" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path98" d="m 427.322,397.172 v -10 -10 -10 -10 -10 -10 -10 -9.565" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path100" d="m 405.991,409.044 h 0.232" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path102" d="m 506.424,283.073 h -3.436 -10 -10 -10 -10 -6.548 -3.543 -10e-4 -10 -2.99" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path104" d="m 406.223,411.917 h 10 10 10 10 10 10 10 10 10 10 10 10 10 7.517" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path106" d="m 518.671,273.927 h 10 10 10 10 10 7.884" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path108" d="m 439.906,273.927 h 6.803 v 0 h 2.704 10 10 10 10 10 10.551 2.65 10e-4 6.056" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path110" d="m 539.678,303.466 h 10 10 10 10 4.417" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path112" d="m 587.169,156.53 v 0" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path114" d="m 543.74,409.452 10,0.029 10,0.03 10,0.03 9.999,0.029 3.43,0.01" />
<path style="fill:none;stroke:#A9713D;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path116" d="m 615.989,393.41 v -10 -10 -10 -10 -10 -10 -10 -10 -6.581" />
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 12 KiB

View File

@ -0,0 +1,64 @@
<svg xmlns="http://www.w3.org/2000/svg" width="384" version="1.1" height="384">
<g transform="translate(-282.71845,-76)" id="RenderLayer_LineSet">
<g id="strokes">
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path2" d="m 405.991,306.829 v 10 10 10 10 10 10 10 10 6.581 5.978 9.656 3.057" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path4" d="m 405.991,409.044 v 0 -9.656 -5.978 -10 -10 -10 -10 -10 -10 -10 -10 -6.581" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path6" d="m 370.692,127.899 v 1.329 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path8" d="m 439.906,283.073 v 0 h -10 -10 -10.303 -3.612 -10 -10 -10 -2.337 l -2.962,-2.901 v 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path10" d="m 373.654,283.073 -2.962,-2.901 v -10 -10 -10 -10 -10 -10 -1.283 -10 -10 -10 -10 -10 -9.658" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path12" d="m 370.692,127.899 h -7.383 -10 -2.899 -5.311 v 0 l -0.45,0.28 -0.37,0.387 -0.268,0.47 v 0.192 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 2.901 10 4.487 5.906 3.363 10 10 10 10 10 10 10 10 6.581 l 6.235,6.039 7.183,6.957 2.643,2.56 3.237,3.135 v 0 h 7.383 2.962 10 10 10 2.337 v 0 0 -3.057" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path14" d="m 584.095,303.466 3.074,3.363 v 10 10 10 10 10 10 10 10 6.581 6.183 9.988 10e-4 0.001 2.518 h 6.497 10 2.976 7.534 v 0 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path16" d="m 615.989,393.41 v -10 -10 -10 -10 -10 -10 -10 -10 -6.581 -3.363 -5.906 -10 -4.487 -2.901 -10 -10 -10 -10 -10 -10 -1.283 -10 -10 -10 -10 -10 -9.658 -2.701 -4.955 -10 -0.947 -10 -1.4 -0.061 l -0.299,-0.524 -0.394,-0.413 -0.019,-0.019 v 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path18" d="m 584.093,129.228 h -10 -10 -10 -10 l -10,-0.001 h -10 -5.476 -10 -10 -10 -10 -10 -10 l -10,-0.001 h -8.828 -10 -10 -10 -0.326 -3.615 l -10,0.001 h -10 l -10,0.001 h -2.205 -2.951 v 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path20" d="m 615.277,128.211 v 0 l -0.501,-0.312 v 0 0 h -8.134 -10 -2.976 -6.497 v 1.329" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path22" d="m 615.69,128.643 0.299,0.524 v 0.061 10 1.4 10 0.947 4.955 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 2.901 10 4.487 5.906 3.363 10 10 10 10 10 10 10 10 6.581 6.183 9.987 0.626 l -0.447,0.784 -0.617,0.644 -0.749,0.467" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path24" d="m 587.169,156.53 v 0 0 2.701 10 10 10 10 10 9.658 10 10 10 10 10 10 1.283 l -3.074,2.901 h -10 -10 -10 -10 -10 -10 -5.424" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path26" d="m 370.692,129.228 v -1.329 0 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path28" d="m 584.093,129.228 h 3.076" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path30" d="m 350.41,140.628 h 10 2.899 v 10 0.947 h -3.555 -9.344 v 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path32" d="m 587.169,129.228 v 10 1.4 10 0.947 4.955" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path34" d="m 350.41,151.575 v -10 -0.947" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path36" d="m 593.666,151.575 v -10 -0.947 0 h 10 2.976" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path38" d="m 606.642,140.628 v 10 0.947 h -10 -2.976 v 0 -10 -0.947" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path40" d="m 615.69,128.643 -0.394,-0.413 -0.019,-0.019 v 0 l -0.501,-0.312" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path42" d="m 615.989,393.41 v 6.183 9.987 0.626 l -0.447,0.783 -0.576,0.603 -0.041,0.042 v 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path44" d="m 614.925,411.634 v 0 l -0.749,0.467" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path46" d="m 615.69,128.643 -0.009,-0.01 -0.404,-0.422 -0.501,-0.312" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path48" d="m 614.176,412.101 0.749,-0.467 v 0 l 0.041,-0.042 0.576,-0.603 0.447,-0.783 v -0.626 -9.987 -6.183" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path50" d="m 406.223,306.613 -0.232,0.216 v 0 l 0.232,-0.216 3.38,-3.147 h 10 10 10.303 10 10 10 10 10 10 10 8.765 10 10 1.007" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path52" d="m 518.671,283.073 v 0 h -10 -2.247" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path54" d="m 615.277,128.211 0.404,0.422" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path56" d="m 383.445,273.927 h 10 10 10 10 10 6.461" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path58" d="m 576.555,273.927 2.03,-0.051 1.978,-0.302 1.707,-0.727" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path60" d="m 582.27,272.847 1.099,-1.131 0.456,-1.309 0.077,-1.342" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path62" d="m 583.902,269.065 v -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -9.834 0 -10 -7.959" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path64" d="m 583.902,141.272 -0.077,-1.344 -0.457,-1.309 -1.098,-1.13" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path66" d="m 582.27,137.489 -1.709,-0.727 -1.977,-0.301 -2.029,-0.051" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path68" d="m 576.555,136.41 h -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -3.11 l -2.03,0.051 -1.978,0.302 -1.707,0.726" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path70" d="m 377.73,137.489 -1.099,1.131 -0.456,1.309 -0.077,1.343" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path72" d="m 376.098,269.065 0.077,1.343 0.457,1.309 1.098,1.13" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path74" d="m 377.73,272.847 1.709,0.727 1.977,0.302 2.029,0.051" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path76" d="m 457.882,318.176 v 10 10 10 10 10 10 10 8.996 l -0.375,1.491 -0.542,1.03" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path78" d="m 456.965,399.693 h -10 -10 -8.726 l -0.542,-1.03 -0.375,-1.491" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path80" d="m 539.678,303.466 -0.064,-0.035 h -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10.198 l -1.889,1.029 -1.304,1.491" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path82" d="m 543.74,411.917 v -2.465 -0.024 -10 -10 -10 -10 -10 -10 -10 -10 -10 -10 -2.742 l -1.686,-1.925 -2.376,-1.295" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path84" d="m 427.612,316.452 0.42,-0.797 h 10 10 8.933 l 0.542,1.03 0.375,1.491" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path86" d="m 427.322,317.607 0.29,-1.155" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path88" d="m 350.41,151.575 v -10 -0.947" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path90" d="m 370.692,127.899 v 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path92" d="m 376.098,141.272 v 10 7.954 0.005 10 10 10 10 10 10 10 10 10 10 9.834" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path94" d="m 405.991,409.044 v 3.057" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path96" d="m 406.223,305.951 v 0.662 0 0 0 10 10 10 10 10 10 10 10 10 10 2.333 0.098 2.873" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path98" d="m 427.322,397.172 v -10 -10 -10 -10 -10 -10 -10 -9.565" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path100" d="m 405.991,409.044 h 0.232" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path102" d="m 506.424,283.073 h -3.436 -10 -10 -10 -10 -6.548 -3.543 -10e-4 -10 -2.99" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path104" d="m 406.223,411.917 h 10 10 10 10 10 10 10 10 10 10 10 10 10 7.517" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path106" d="m 518.671,273.927 h 10 10 10 10 10 7.884" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path108" d="m 439.906,273.927 h 6.803 v 0 h 2.704 10 10 10 10 10 10.551 2.65 10e-4 6.056" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path110" d="m 539.678,303.466 h 10 10 10 10 4.417" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path112" d="m 587.169,156.53 v 0" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path114" d="m 543.74,409.452 10,0.029 10,0.03 10,0.03 9.999,0.029 3.43,0.01" />
<path style="fill:none;stroke:#CB7590;stroke-width:3;stroke-linecap:butt;stroke-linejoin:round;stroke-opacity:1" id="path116" d="m 615.989,393.41 v -10 -10 -10 -10 -10 -10 -10 -10 -6.581" />
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 786 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 398 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 497 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 356 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 390 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 452 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 589 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 561 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 328 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 457 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 384 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 326 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 437 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 599 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 383 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 411 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 282 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 337 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 688 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 639 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 498 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 149 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 184 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 263 B

View File

@ -65,6 +65,8 @@ const getUnitDelay = units => {
}
};
const fallbackFormat = new Intl.DateTimeFormat('en', shortDateFormatOptions);
export const timeAgoString = (intl, date, now, year) => {
const delta = now - date.getTime();

View File

@ -356,6 +356,7 @@ class Status extends ImmutablePureComponent {
{prepend}
<div className={classNames('status', `status-${status.get('visibility')}`, { 'status-reply': !!status.get('in_reply_to_id'), muted: this.props.muted, read: unread === false })} data-id={status.get('id')}>
<div className='status__expand' onClick={this.handleClick} role='presentation' />
<div className='status__info'>
<a href={status.get('url')} className='status__relative-time' target='_blank' rel='noopener'><RelativeTimestamp timestamp={status.get('created_at')} /></a>
@ -370,14 +371,15 @@ class Status extends ImmutablePureComponent {
<StatusContent status={status} onClick={this.handleClick} expanded={!status.get('hidden')} onExpandedToggle={this.handleExpandedToggle} collapsable />
{media}
{showThread && status.get('in_reply_to_id') && status.get('in_reply_to_account_id') === status.getIn(['account', 'id']) && (
<button className='status__content__read-more-button' onClick={this.handleClick}>
<i className='fa fa-fw fa-sort-amount-desc status__prepend-icon' />
<FormattedMessage id='status.show_thread' defaultMessage='Show thread' />
</button>
)}
{media}
<StatusActionBar status={status} account={account} {...other} />
</div>
</div>

View File

@ -249,9 +249,9 @@ class StatusActionBar extends ImmutablePureComponent {
return (
<div className='status__action-bar'>
<div className='status__action-bar__counter'><IconButton className='status__action-bar-button' title={replyTitle} icon={status.get('in_reply_to_account_id') === status.getIn(['account', 'id']) ? 'reply' : replyIcon} onClick={this.handleReplyClick} /><span className='status__action-bar__counter__label' >{obfuscatedCount(status.get('replies_count'))}</span></div>
<div className='status__action-bar__counter'><IconButton className='status__action-bar-button' title={replyTitle} icon={status.get('in_reply_to_account_id') === status.getIn(['account', 'id']) ? 'reply' : replyIcon} onClick={this.handleReplyClick} /></div>
<IconButton className='status__action-bar-button' disabled={!publicStatus} active={status.get('reblogged')} pressed={status.get('reblogged')} title={!publicStatus ? intl.formatMessage(messages.cannot_reblog) : intl.formatMessage(messages.reblog)} icon={reblogIcon} onClick={this.handleReblogClick} />
<IconButton className='status__action-bar-button star-icon' animate active={status.get('favourited')} pressed={status.get('favourited')} title={intl.formatMessage(messages.favourite)} icon='star' onClick={this.handleFavouriteClick} />
<IconButton className='status__action-bar-button star-icon' animate active={status.get('favourited')} pressed={status.get('favourited')} title={intl.formatMessage(messages.favourite)} icon='floppy-o' onClick={this.handleFavouriteClick} />
{shareButton}
<div className='status__action-bar-dropdown'>

View File

@ -7,6 +7,7 @@ import { hydrateStore } from '../actions/store';
import { IntlProvider, addLocaleData } from 'react-intl';
import { getLocale } from '../locales';
import PublicTimeline from '../features/standalone/public_timeline';
import CommunityTimeline from '../features/standalone/community_timeline';
import HashtagTimeline from '../features/standalone/hashtag_timeline';
import ModalContainer from '../features/ui/containers/modal_container';
import initialState from '../initial_state';
@ -25,22 +26,24 @@ export default class TimelineContainer extends React.PureComponent {
static propTypes = {
locale: PropTypes.string.isRequired,
hashtag: PropTypes.string,
local: PropTypes.bool,
showPublicTimeline: PropTypes.bool.isRequired,
};
static defaultProps = {
local: !initialState.settings.known_fediverse,
showPublicTimeline: initialState.settings.known_fediverse,
};
render () {
const { locale, hashtag, local } = this.props;
const { locale, hashtag, showPublicTimeline } = this.props;
let timeline;
if (hashtag) {
timeline = <HashtagTimeline hashtag={hashtag} />;
} else if (showPublicTimeline) {
timeline = <PublicTimeline />;
} else {
timeline = <PublicTimeline local={local} />;
timeline = <CommunityTimeline />;
}
return (
@ -48,7 +51,6 @@ export default class TimelineContainer extends React.PureComponent {
<Provider store={store}>
<Fragment>
{timeline}
{ReactDOM.createPortal(
<ModalContainer />,
document.getElementById('modal-container'),

View File

@ -2,6 +2,7 @@ import React from 'react';
import PropTypes from 'prop-types';
import ImmutablePropTypes from 'react-immutable-proptypes';
import ImmutablePureComponent from 'react-immutable-pure-component';
import Icon from 'mastodon/components/icon';
import { autoPlayGif, displayMedia } from 'mastodon/initial_state';
import classNames from 'classnames';
import { decode } from 'blurhash';
@ -88,8 +89,10 @@ export default class MediaItem extends ImmutablePureComponent {
const width = `${Math.floor((displayWidth - 4) / 3) - 4}px`;
const height = width;
const status = attachment.get('status');
const title = status.get('spoiler_text') || attachment.get('description');
let thumbnail = '';
let icon;
if (attachment.get('type') === 'unknown') {
// Skip
@ -131,11 +134,20 @@ export default class MediaItem extends ImmutablePureComponent {
);
}
if (!visible) {
icon = (
<span className='account-gallery__item__icons'>
<Icon id='eye-slash' />
</span>
);
}
return (
<div className='account-gallery__item' style={{ width, height }}>
<a className='media-gallery__item-thumbnail' href={status.get('url')} target='_blank' onClick={this.handleClick}>
<a className='media-gallery__item-thumbnail' href={status.get('url')} target='_blank' onClick={this.handleClick} title={title}>
<canvas width={32} height={32} ref={this.setCanvasRef} className={classNames('media-gallery__preview', { 'media-gallery__preview--hidden': visible && loaded })} />
{visible && thumbnail}
{!visible && icon}
</a>
</div>
);

View File

@ -86,7 +86,7 @@ class ComposeForm extends ImmutablePureComponent {
const { isSubmitting, isChangingUpload, isUploading, anyMedia } = this.props;
const fulltext = [this.props.spoilerText, countableText(this.props.text)].join('');
if (isSubmitting || isUploading || isChangingUpload || length(fulltext) > 500 || (fulltext.length !== 0 && fulltext.trim().length === 0 && !anyMedia)) {
if (isSubmitting || isUploading || isChangingUpload || length(fulltext) > 512 || (fulltext.length !== 0 && fulltext.trim().length === 0 && !anyMedia)) {
return;
}
@ -162,7 +162,7 @@ class ComposeForm extends ImmutablePureComponent {
const { intl, onPaste, showSearch, anyMedia } = this.props;
const disabled = this.props.isSubmitting;
const text = [this.props.spoilerText, countableText(this.props.text)].join('');
const disabledButton = disabled || this.props.isUploading || this.props.isChangingUpload || length(text) > 500 || (text.length !== 0 && text.trim().length === 0 && !anyMedia);
const disabledButton = disabled || this.props.isUploading || this.props.isChangingUpload || length(text) > 512 || (text.length !== 0 && text.trim().length === 0 && !anyMedia);
let publishText = '';
if (this.props.privacy === 'private' || this.props.privacy === 'direct') {
@ -215,7 +215,7 @@ class ComposeForm extends ImmutablePureComponent {
<PrivacyDropdownContainer />
<SpoilerButtonContainer />
</div>
<div className='character-counter__wrapper'><CharacterCounter max={500} text={text} /></div>
<div className='character-counter__wrapper'><CharacterCounter max={512} text={text} /></div>
</div>
<div className='compose-form__publish'>

View File

@ -357,8 +357,8 @@ class EmojiPickerDropdown extends React.PureComponent {
<div ref={this.setTargetRef} className='emoji-button' title={title} aria-label={title} aria-expanded={active} role='button' onClick={this.onToggle} onKeyDown={this.onToggle} tabIndex={0}>
<img
className={classNames('emojione', { 'pulse-loading': active && loading })}
alt='🙂'
src={`${assetHost}/emoji/1f602.svg`}
alt='🤔'
src={`${assetHost}/emoji/1f914.svg`}
/>
</div>

View File

@ -20,7 +20,7 @@ const mapStateToProps = state => ({
focusDate: state.getIn(['compose', 'focusDate']),
caretPosition: state.getIn(['compose', 'caretPosition']),
preselectDate: state.getIn(['compose', 'preselectDate']),
is_submitting: state.getIn(['compose', 'is_submitting']),
isSubmitting: state.getIn(['compose', 'is_submitting']),
isChangingUpload: state.getIn(['compose', 'is_changing_upload']),
isUploading: state.getIn(['compose', 'is_uploading']),
showSearch: state.getIn(['search', 'submitted']) && !state.getIn(['search', 'hidden']),

View File

@ -12,13 +12,13 @@ const DEFAULTS = [
'+1',
'grinning',
'kissing_heart',
'heart_eyes',
'vhs',
'laughing',
'stuck_out_tongue_winking_eye',
'floppy_disk',
'sweat_smile',
'joy',
'yum',
'disappointed',
'computer',
'thinking_face',
'weary',
'sob',

View File

@ -4,7 +4,6 @@ import PropTypes from 'prop-types';
import classNames from 'classnames';
import { changeComposeSensitivity } from 'mastodon/actions/compose';
import { injectIntl, defineMessages, FormattedMessage } from 'react-intl';
import Icon from 'mastodon/components/icon';
const messages = defineMessages({
marked: { id: 'compose_form.sensitive.marked', defaultMessage: 'Media is marked as sensitive' },
@ -38,9 +37,19 @@ class SensitiveButton extends React.PureComponent {
return (
<div className='compose-form__sensitive-button'>
<button className={classNames('icon-button', { active })} onClick={onClick} disabled={disabled} title={intl.formatMessage(active ? messages.marked : messages.unmarked)}>
<Icon id='eye-slash' /> <FormattedMessage id='compose_form.sensitive.hide' defaultMessage='Mark media as sensitive' />
</button>
<label className={classNames('icon-button', { active })} title={intl.formatMessage(active ? messages.marked : messages.unmarked)}>
<input
name='mark-sensitive'
type='checkbox'
checked={active}
onChange={onClick}
disabled={disabled}
/>
<span className={classNames('checkbox', { active })} />
<FormattedMessage id='compose_form.sensitive.hide' defaultMessage='Mark media as sensitive' />
</label>
</div>
);
}

View File

@ -15,20 +15,20 @@ import NavigationBar from '../compose/components/navigation_bar';
import Icon from 'mastodon/components/icon';
const messages = defineMessages({
home_timeline: { id: 'tabs_bar.home', defaultMessage: 'Home' },
notifications: { id: 'tabs_bar.notifications', defaultMessage: 'Notifications' },
public_timeline: { id: 'navigation_bar.public_timeline', defaultMessage: 'Federated timeline' },
home_timeline: { id: 'tabs_bar.home', defaultMessage: '/timelines/home' },
notifications: { id: 'tabs_bar.notifications', defaultMessage: '~/.notifications' },
public_timeline: { id: 'navigation_bar.public_timeline', defaultMessage: '/timelines/federated' },
settings_subheading: { id: 'column_subheading.settings', defaultMessage: 'Settings' },
community_timeline: { id: 'navigation_bar.community_timeline', defaultMessage: 'Local timeline' },
direct: { id: 'navigation_bar.direct', defaultMessage: 'Direct messages' },
preferences: { id: 'navigation_bar.preferences', defaultMessage: 'Preferences' },
follow_requests: { id: 'navigation_bar.follow_requests', defaultMessage: 'Follow requests' },
favourites: { id: 'navigation_bar.favourites', defaultMessage: 'Favourites' },
blocks: { id: 'navigation_bar.blocks', defaultMessage: 'Blocked users' },
domain_blocks: { id: 'navigation_bar.domain_blocks', defaultMessage: 'Hidden domains' },
mutes: { id: 'navigation_bar.mutes', defaultMessage: 'Muted users' },
pins: { id: 'navigation_bar.pins', defaultMessage: 'Pinned toots' },
lists: { id: 'navigation_bar.lists', defaultMessage: 'Lists' },
community_timeline: { id: 'navigation_bar.community_timeline', defaultMessage: '/timelines/local' },
direct: { id: 'navigation_bar.direct', defaultMessage: '~/.dms' },
preferences: { id: 'navigation_bar.preferences', defaultMessage: 'edit ~/.config' },
follow_requests: { id: 'navigation_bar.follow_requests', defaultMessage: '~/.follow-requests' },
favourites: { id: 'navigation_bar.favourites', defaultMessage: '~/.florps' },
blocks: { id: 'navigation_bar.blocks', defaultMessage: '~/.blocked' },
domain_blocks: { id: 'navigation_bar.domain_blocks', defaultMessage: '~/.muted/domains' },
mutes: { id: 'navigation_bar.mutes', defaultMessage: '~/.muted' },
pins: { id: 'navigation_bar.pins', defaultMessage: '~/.pinned' },
lists: { id: 'navigation_bar.lists', defaultMessage: '~/.lists' },
discover: { id: 'navigation_bar.discover', defaultMessage: 'Discover' },
personal: { id: 'navigation_bar.personal', defaultMessage: 'Personal' },
security: { id: 'navigation_bar.security', defaultMessage: 'Security' },
@ -159,11 +159,8 @@ class GettingStarted extends ImmutablePureComponent {
<ul>
{invitesEnabled && <li><a href='/invites' target='_blank'><FormattedMessage id='getting_started.invite' defaultMessage='Invite people' /></a> · </li>}
{multiColumn && <li><Link to='/keyboard-shortcuts'><FormattedMessage id='navigation_bar.keyboard_shortcuts' defaultMessage='Hotkeys' /></Link> · </li>}
<li><a href='/auth/edit'><FormattedMessage id='getting_started.security' defaultMessage='Security' /></a> · </li>
<li><a href='/about/more' target='_blank'><FormattedMessage id='navigation_bar.info' defaultMessage='About this server' /></a> · </li>
<li><a href='https://joinmastodon.org/apps' target='_blank'><FormattedMessage id='navigation_bar.apps' defaultMessage='Mobile apps' /></a> · </li>
<li><a href='/terms' target='_blank'><FormattedMessage id='getting_started.terms' defaultMessage='Terms of service' /></a> · </li>
<li><a href='/settings/applications' target='_blank'><FormattedMessage id='getting_started.developers' defaultMessage='Developers' /></a> · </li>
<li><a href='https://docs.joinmastodon.org' target='_blank'><FormattedMessage id='getting_started.documentation' defaultMessage='Documentation' /></a> · </li>
<li><a href='/auth/sign_out' data-method='delete'><FormattedMessage id='navigation_bar.logout' defaultMessage='Logout' /></a></li>
</ul>
@ -171,8 +168,8 @@ class GettingStarted extends ImmutablePureComponent {
<p>
<FormattedMessage
id='getting_started.open_source_notice'
defaultMessage='Mastodon is open source software. You can contribute or report issues on GitHub at {github}.'
values={{ github: <span><a href={source_url} rel='noopener' target='_blank'>{repository}</a> (v{version})</span> }}
defaultMessage='Cybrespace is open source software. You can contribute or report issues on GitHub at {github}.'
values={{ github: <a href='https://cybre.tech/cybrespace/mastodon' rel='noopener' target='_blank'>cybrespace/mastodon</a> }}
/>
</p>
</div>

View File

@ -149,7 +149,7 @@ class Notification extends ImmutablePureComponent {
<div className='notification notification-favourite focusable' tabIndex='0' aria-label={notificationForScreenReader(intl, intl.formatMessage({ id: 'notification.favourite', defaultMessage: '{name} favourited your status' }, { name: notification.getIn(['account', 'acct']) }), notification.get('created_at'))}>
<div className='notification__message'>
<div className='notification__favourite-icon-wrapper'>
<Icon id='star' className='star-icon' fixedWidth />
<Icon id='floppy-o' className='star-icon' fixedWidth />
</div>
<span title={notification.get('created_at')}>

View File

@ -0,0 +1,71 @@
import React from 'react';
import { connect } from 'react-redux';
import PropTypes from 'prop-types';
import StatusListContainer from '../../ui/containers/status_list_container';
import { expandCommunityTimeline } from '../../../actions/timelines';
import Column from '../../../components/column';
import ColumnHeader from '../../../components/column_header';
import { defineMessages, injectIntl } from 'react-intl';
import { connectCommunityStream } from '../../../actions/streaming';
const messages = defineMessages({
title: { id: 'standalone.public_title', defaultMessage: 'A look inside...' },
});
export default @connect()
@injectIntl
class CommunityTimeline extends React.PureComponent {
static propTypes = {
dispatch: PropTypes.func.isRequired,
intl: PropTypes.object.isRequired,
};
handleHeaderClick = () => {
this.column.scrollTop();
}
setRef = c => {
this.column = c;
}
componentDidMount () {
const { dispatch } = this.props;
dispatch(expandCommunityTimeline());
this.disconnect = dispatch(connectCommunityStream());
}
componentWillUnmount () {
if (this.disconnect) {
this.disconnect();
this.disconnect = null;
}
}
handleLoadMore = maxId => {
this.props.dispatch(expandCommunityTimeline({ maxId }));
}
render () {
const { intl } = this.props;
return (
<Column ref={this.setRef} label={intl.formatMessage(messages.title)}>
<ColumnHeader
icon='users'
title={intl.formatMessage(messages.title)}
onClick={this.handleHeaderClick}
/>
<StatusListContainer
timelineId='community'
onLoadMore={this.handleLoadMore}
scrollKey='standalone_public_timeline'
trackScroll={false}
/>
</Column>
);
}
}

View File

@ -196,7 +196,7 @@ class ActionBar extends React.PureComponent {
<div className='detailed-status__action-bar'>
<div className='detailed-status__button'><IconButton title={intl.formatMessage(messages.reply)} icon={status.get('in_reply_to_account_id') === status.getIn(['account', 'id']) ? 'reply' : replyIcon} onClick={this.handleReplyClick} /></div>
<div className='detailed-status__button'><IconButton disabled={reblog_disabled} active={status.get('reblogged')} title={reblog_disabled ? intl.formatMessage(messages.cannot_reblog) : intl.formatMessage(messages.reblog)} icon={reblogIcon} onClick={this.handleReblogClick} /></div>
<div className='detailed-status__button'><IconButton className='star-icon' animate active={status.get('favourited')} title={intl.formatMessage(messages.favourite)} icon='star' onClick={this.handleFavouriteClick} /></div>
<div className='detailed-status__button'><IconButton className='star-icon' animate active={status.get('favourited')} title={intl.formatMessage(messages.favourite)} icon='floppy-o' onClick={this.handleFavouriteClick} /></div>
{shareButton}
<div className='detailed-status__action-bar-dropdown'>

View File

@ -174,7 +174,7 @@ export default class DetailedStatus extends ImmutablePureComponent {
if (this.context.router) {
favouriteLink = (
<Link to={`/statuses/${status.get('id')}/favourites`} className='detailed-status__link'>
<Icon id='star' />
<Icon id='floppy-o' />
<span className='detailed-status__favorites'>
<FormattedNumber value={status.get('favourites_count')} />
</span>
@ -183,7 +183,7 @@ export default class DetailedStatus extends ImmutablePureComponent {
} else {
favouriteLink = (
<a href={`/interact/${status.get('id')}?type=favourite`} className='detailed-status__link' onClick={this.handleModalLink}>
<Icon id='star' />
<Icon id='floppy-o' />
<span className='detailed-status__favorites'>
<FormattedNumber value={status.get('favourites_count')} />
</span>

View File

@ -0,0 +1,293 @@
{
"account.block": "Block @{name}",
"account.block_domain": "Hide everything from {domain}",
"account.blocked": "Blocked",
"account.disclaimer_full": "THESE NUMBERS ARE THE STUFF WHAT YOUR SERVER KNOWS ABOUT AND THERE MIGHT BE MORE THAT IT DONT KNOW ABOUT.",
"account.domain_blocked": "Domain hidden",
"account.edit_profile": "edit ~/.profile",
"account.follow": "Follow",
"account.followers": "Followers",
"account.follows": "Follows",
"account.follows_you": "Follows you",
"account.hide_reblogs": "Hide boosts from @{name}",
"account.media": "Media",
"account.mention": "Mention @{name}",
"account.moved_to": "{name} has moved to:",
"account.mute": "Mute @{name}",
"account.mute_notifications": "Mute notifications from @{name}",
"account.muted": "Muted",
"account.posts": "Pings",
"account.posts_with_replies": "Pings with replies",
"account.report": "Report @{name}",
"account.requested": "Awaiting approval. Click to cancel follow request",
"account.share": "Share @{name}'s profile",
"account.show_reblogs": "Show boosts from @{name}",
"account.unblock": "Unblock @{name}",
"account.unblock_domain": "Unhide {domain}",
"account.unfollow": "Unfollow",
"account.unmute": "Unmute @{name}",
"account.unmute_notifications": "Unmute notifications from @{name}",
"account.view_full_profile": "View full profile",
"boost_modal.combo": "You can press {combo} to skip this next time",
"bundle_column_error.body": "Something went wrong while loading this component.",
"bundle_column_error.retry": "Try again",
"bundle_column_error.title": "Network error",
"bundle_modal_error.close": "Close",
"bundle_modal_error.message": "Something went wrong while loading this component.",
"bundle_modal_error.retry": "Try again",
"column.blocks": "~/.blocked",
"column.community": "/timelines/local",
"column.direct": "~/.dms",
"column.favourites": "~/.florps",
"column.follow_requests": "~/.follow-requests",
"column.home": "/timelines/home",
"column.lists": "Lists",
"column.mutes": "~/.muted",
"column.notifications": "~/.notifications",
"column.pins": "~/.pinned",
"column.public": "/timelines/federated",
"column_back_button.label": "Back",
"column_header.hide_settings": "Hide settings",
"column_header.moveLeft_settings": "Move column to the left",
"column_header.moveRight_settings": "Move column to the right",
"column_header.pin": "Pin",
"column_header.show_settings": "Show settings",
"column_header.unpin": "Unpin",
"column_subheading.navigation": "Navigation",
"column_subheading.settings": "Settings",
"compose.attach": "Attach...",
"compose.attach.doodle": "Draw something",
"compose.attach.upload": "Upload a file",
"compose_form.hashtag_warning": "This ping won't be listed under any hashtag as it is unlisted. Only public pings can be searched by hashtag.",
"compose_form.lock_disclaimer": "Your account is not {locked}. Anyone can follow you to view your follower-only posts.",
"compose_form.lock_disclaimer.lock": "locked",
"compose_form.placeholder": "What is in your databanks?",
"compose_form.publish": "Ping",
"compose_form.publish_loud": "{publish}!",
"compose_form.sensitive.marked": "Media is marked as sensitive",
"compose_form.sensitive.unmarked": "Media is not marked as sensitive",
"compose_form.spoiler.marked": "Text is hidden behind warning",
"compose_form.spoiler.unmarked": "Text is not hidden",
"compose_form.spoiler_placeholder": "Write your warning here",
"confirmation_modal.cancel": "Cancel",
"confirmations.block.confirm": "Block",
"confirmations.block.message": "Are you sure you want to block {name}?",
"confirmations.delete.confirm": "Delete",
"confirmations.delete.message": "Are you sure you want to delete this status?",
"confirmations.delete_list.confirm": "Delete",
"confirmations.delete_list.message": "Are you sure you want to permanently delete this list?",
"confirmations.domain_block.confirm": "Hide entire domain",
"confirmations.domain_block.message": "Are you really, really sure you want to block the entire {domain}? In most cases a few targeted blocks or mutes are sufficient and preferable.",
"confirmations.mute.confirm": "Mute",
"confirmations.mute.message": "Are you sure you want to mute {name}?",
"confirmations.unfollow.confirm": "Unfollow",
"confirmations.unfollow.message": "Are you sure you want to unfollow {name}?",
"doodle_button.label": "Add a drawing",
"embed.instructions": "Embed this status on your website by copying the code below.",
"embed.preview": "Here is what it will look like:",
"emoji_button.activity": "Activity",
"emoji_button.custom": "Custom",
"emoji_button.flags": "Flags",
"emoji_button.food": "Food & Drink",
"emoji_button.label": "Insert emoji",
"emoji_button.nature": "Nature",
"emoji_button.not_found": "No emojos!! (╯°□°)╯︵ ┻━┻",
"emoji_button.objects": "Objects",
"emoji_button.people": "People",
"emoji_button.recent": "Frequently used",
"emoji_button.search": "Search...",
"emoji_button.search_results": "Search results",
"emoji_button.symbols": "Symbols",
"emoji_button.travel": "Travel & Places",
"empty_column.community": "The local timeline is empty. Write something publicly to get the ball rolling!",
"empty_column.direct": "You don't have any direct messages yet. When you send or receive one, it will show up here.",
"empty_column.hashtag": "There is nothing in this hashtag yet.",
"empty_column.home": "Your home timeline is empty! Visit {public} or use query to get started and meet other users.",
"empty_column.home.public_timeline": "the public timeline",
"empty_column.list": "There is nothing in this list yet. When members of this list post new statuses, they will appear here.",
"empty_column.notifications": "You don't have any notifications yet. Interact with others to start the conversation.",
"empty_column.public": "There is nothing here! Write something publicly, or manually follow users from other instances to fill it up",
"follow_request.authorize": "Authorize",
"follow_request.reject": "Reject",
"getting_started.appsshort": "Apps",
"getting_started.faq": "FAQ",
"getting_started.heading": "Getting started",
"getting_started.open_source_notice": "Mastodon is open source software. You can contribute or report issues on GitHub at {github}.",
"getting_started.userguide": "User Guide",
"home.column_settings.advanced": "Advanced",
"home.column_settings.basic": "Basic",
"home.column_settings.filter_regex": "Filter out by regular expressions",
"home.column_settings.show_reblogs": "Show relays",
"home.column_settings.show_replies": "Show replies",
"home.settings": "Column settings",
"keyboard_shortcuts.back": "to navigate back",
"keyboard_shortcuts.boost": "to boost",
"keyboard_shortcuts.column": "to focus a status in one of the columns",
"keyboard_shortcuts.compose": "to focus the compose textarea",
"keyboard_shortcuts.description": "Description",
"keyboard_shortcuts.down": "to move down in the list",
"keyboard_shortcuts.enter": "to open status",
"keyboard_shortcuts.favourite": "to favourite",
"keyboard_shortcuts.heading": "Keyboard Shortcuts",
"keyboard_shortcuts.hotkey": "Hotkey",
"keyboard_shortcuts.legend": "to display this legend",
"keyboard_shortcuts.mention": "to mention author",
"keyboard_shortcuts.reply": "to reply",
"keyboard_shortcuts.search": "to focus search",
"keyboard_shortcuts.toot": "to start a brand new ping",
"keyboard_shortcuts.unfocus": "to un-focus compose textarea/search",
"keyboard_shortcuts.up": "to move up in the list",
"lightbox.close": "Close",
"lightbox.next": "Next",
"lightbox.previous": "Previous",
"lists.account.add": "Add to list",
"lists.account.remove": "Remove from list",
"lists.delete": "Delete list",
"lists.edit": "Edit list",
"lists.new.create": "Add list",
"lists.new.title_placeholder": "New list title",
"lists.search": "Search among people you follow",
"lists.subheading": "Your lists",
"loading_indicator.label": "Loading...",
"media_gallery.toggle_visible": "Toggle visibility",
"missing_indicator.label": "Not found",
"missing_indicator.sublabel": "This resource could not be found",
"mute_modal.hide_notifications": "Hide notifications from this user?",
"navigation_bar.blocks": "~/.blocks",
"navigation_bar.community_timeline": "/timelines/local",
"navigation_bar.direct": "~/.dms",
"navigation_bar.edit_profile": "edit ~/.profile",
"navigation_bar.favourites": "~/.florps",
"navigation_bar.follow_requests": "~/.follow-requests",
"navigation_bar.info": "/about/more",
"navigation_bar.keyboard_shortcuts": "~/.kbd/shortcuts.conf",
"navigation_bar.lists": "~/.lists",
"navigation_bar.logout": "Jack out",
"navigation_bar.mutes": "~/.muted",
"navigation_bar.pins": "~/.pinned",
"navigation_bar.preferences": "edit ~/.config",
"navigation_bar.public_timeline": "/timelines/federated",
"notification.favourite": "{name} florped your ping",
"notification.follow": "{name} followed you",
"notification.mention": "{name} mentioned you",
"notification.reblog": "{name} relayed your ping",
"notifications.clear": "Clear notifications",
"notifications.clear_confirmation": "Are you sure you want to permanently clear all your notifications?",
"notifications.column_settings.alert": "Desktop notifications",
"notifications.column_settings.favourite": "Favourites:",
"notifications.column_settings.follow": "New followers:",
"notifications.column_settings.mention": "Mentions:",
"notifications.column_settings.push": "Push notifications",
"notifications.column_settings.push_meta": "This device",
"notifications.column_settings.reblog": "Boosts:",
"notifications.column_settings.show": "Show in column",
"notifications.column_settings.sound": "Play sound",
"onboarding.done": "Done",
"onboarding.next": "Next",
"onboarding.page_five.public_timelines": "The local timeline shows public posts from everyone on {domain}. The federated timeline shows public posts from everyone who people on {domain} follow. These are the Public Timelines, a great way to discover new people.",
"onboarding.page_four.home": "The home timeline shows posts from people you follow.",
"onboarding.page_four.notifications": "The notifications column shows when someone interacts with you.",
"onboarding.page_one.federation": "Mastodon is a network of independent servers joining up to make one larger social network. We call these servers instances.",
"onboarding.page_one.full_handle": "Your full handle",
"onboarding.page_one.handle_hint": "This is what you would tell your friends to search for.",
"onboarding.page_one.welcome": "Welcome to Mastodon!",
"onboarding.page_six.admin": "Your instance's admin is {admin}.",
"onboarding.page_six.almost_done": "Almost done...",
"onboarding.page_six.appetoot": "Hang ten on the cybrewaves!",
"onboarding.page_six.apps_available": "There are {apps} available for iOS, Android and other platforms.",
"onboarding.page_six.github": "Mastodon is free open-source software. You can report bugs, request features, or contribute to the code on {github}.",
"onboarding.page_six.guidelines": "community guidelines",
"onboarding.page_six.read_guidelines": "Please read {domain}'s {guidelines}!",
"onboarding.page_six.various_app": "mobile apps",
"onboarding.page_three.profile": "Edit your profile to change your avatar, bio, and display name. There, you will also find other preferences.",
"onboarding.page_three.search": "Use the search bar to find people and look at hashtags, such as {illustration} and {introductions}. To look for a person who is not on this instance, use their full handle.",
"onboarding.page_two.compose": "Write posts from the compose column. You can upload images, change privacy settings, and add content warnings with the icons below.",
"onboarding.skip": "Skip",
"privacy.change": "Adjust status privacy",
"privacy.direct.long": "Post to mentioned users only",
"privacy.direct.short": "Direct",
"privacy.private.long": "Post to followers only",
"privacy.private.short": "Followers-only",
"privacy.public.long": "Post to public timelines",
"privacy.public.short": "Public",
"privacy.unlisted.long": "Do not post to public timelines",
"privacy.unlisted.short": "Unlisted",
"regeneration_indicator.label": "Loading…",
"regeneration_indicator.sublabel": "Your home feed is being prepared!",
"relative_time.days": "{number}d",
"relative_time.hours": "{number}h",
"relative_time.just_now": "now",
"relative_time.minutes": "{number}m",
"relative_time.seconds": "{number}s",
"reply_indicator.cancel": "Cancel",
"report.forward": "Forward to {target}",
"report.forward_hint": "The account is from another server. Send an anonymized copy of the report there as well?",
"report.hint": "The report will be sent to your instance moderators. You can provide an explanation of why you are reporting this account below:",
"report.placeholder": "Additional comments",
"report.submit": "Submit",
"report.target": "Reporting {target}",
"search.placeholder": "Query...",
"search_popout.search_format": "Advanced search format",
"search_popout.tips.full_text": "Simple text returns statuses you have written, favourited, boosted, or have been mentioned in, as well as matching usernames, display names, and hashtags.",
"search_popout.tips.hashtag": "hashtag",
"search_popout.tips.status": "status",
"search_popout.tips.text": "Simple text returns matching display names, usernames and hashtags",
"search_popout.tips.user": "user",
"search_results.accounts": "People",
"search_results.hashtags": "Hashtags",
"search_results.statuses": "Pings",
"search_results.total": "{count, number} {count, plural, one {result} other {results}}",
"standalone.public_title": "Peer into the data grid...",
"status.block": "Block @{name}",
"status.cannot_reblog": "This ping cannot be relayed",
"status.delete": "Delete",
"status.embed": "Embed",
"status.favourite": "Florp",
"status.load_more": "Load more",
"status.media_hidden": "Media hidden",
"status.mention": "Mention @{name}",
"status.more": "More",
"status.mute": "Mute @{name}",
"status.mute_conversation": "Mute conversation",
"status.open": "Expand this status",
"status.pin": "Pin on profile",
"status.pinned": "Pinned ping",
"status.reblog": "Relay",
"status.reblogged_by": "{name} relayed",
"status.reply": "Reply",
"status.replyAll": "Reply to thread",
"status.report": "Report @{name}",
"status.sensitive_toggle": "Click to view",
"status.sensitive_warning": "Sensitive content",
"status.share": "Share",
"status.show_less": "Show less",
"status.show_less_all": "Show less for all",
"status.show_more": "Show more",
"status.show_more_all": "Show more for all",
"status.unmute_conversation": "Unmute conversation",
"status.unpin": "Unpin from profile",
"tabs_bar.federated_timeline": "/timelines/federated",
"tabs_bar.home": "/timelines/home",
"tabs_bar.local_timeline": "/timelines/local",
"tabs_bar.notifications": "~/.notifications",
"ui.beforeunload": "Your draft will be lost if you leave Mastodon.",
"upload_area.title": "Drag & drop to upload",
"upload_button.label": "Add media",
"upload_form.description": "Describe for the visually impaired",
"upload_form.focus": "Crop",
"upload_form.undo": "Undo",
"upload_progress.label": "Uploading...",
"video.close": "Close video",
"video.exit_fullscreen": "Exit full screen",
"video.expand": "Expand video",
"video.fullscreen": "Full screen",
"video.hide": "Hide video",
"video.mute": "Mute sound",
"video.pause": "Pause",
"video.play": "Play",
"video.unmute": "Unmute sound",
"video_player.expand": "Expand video",
"video_player.toggle_sound": "Toggle sound",
"video_player.toggle_visible": "Toggle visibility",
"video_player.video_error": "Video could not be played"
}

View File

@ -0,0 +1,2 @@
[
]

View File

@ -8,3 +8,5 @@ loadPolyfills().then(() => {
}).catch(e => {
console.error(e);
});
require('what-input');

View File

@ -18,6 +18,12 @@ window.addEventListener('message', e => {
id: data.id,
height: document.getElementsByTagName('html')[0].scrollHeight,
}, '*');
if (document.fonts && document.fonts.ready) {
document.fonts.ready.then(sizeBioText);
} else {
sizeBioText();
}
});
});
@ -116,6 +122,17 @@ function main() {
document.head.appendChild(scrollbarWidthStyle);
scrollbarWidthStyle.sheet.insertRule(`body.with-modals--active { margin-right: ${scrollbarWidth}px; }`, 0);
}
[].forEach.call(document.querySelectorAll('[data-component="Card"]'), (content) => {
const props = JSON.parse(content.getAttribute('data-props'));
ReactDOM.render(<CardContainer locale={locale} {...props} />, content);
});
if (document.fonts && document.fonts.ready) {
document.fonts.ready.then(sizeBioText);
} else {
sizeBioText();
}
});
delegate(document, '.webapp-btn', 'click', ({ target, button }) => {
@ -237,6 +254,22 @@ function main() {
input.readonly = oldReadOnly;
});
delegate(document, '#account_note', 'input', sizeBioText);
function sizeBioText() {
const noteCounter = document.querySelector('.note-counter');
const bioTextArea = document.querySelector('#account_note');
if (noteCounter) {
noteCounter.textContent = 413 - length(bioTextArea.value);
}
if (bioTextArea) {
bioTextArea.style.height = 'auto';
bioTextArea.style.height = (bioTextArea.scrollHeight+3) + 'px';
}
}
}
loadPolyfills().then(main).catch(error => {

View File

@ -67,3 +67,11 @@
text-decoration: none;
}
}
.nothing-here {
color: $darker-text-color;
}
.public-layout .public-account-header__tabs__tabs .counter.active::after {
border-bottom: 4px solid $ui-highlight-color;
}

View File

@ -0,0 +1,81 @@
@import 'application';
/* Allow columns to grow wider as the screen gets
* wider, but don't ever let them get more than
* 400px (some people have a bunch of columns!) */
@media screen and (min-width: 1300px) {
.column {
flex-grow: 1 !important;
max-width: 400px;
}
.drawer {
width: 17%; /* Not part of the flex fun */
max-width: 400px;
min-width: 330px;
}
}
/* Cap the column height at 100vh (fixed an old
* bug someone encountered in safari, but which
* I've seen resurface from time to time) */
.column {
max-height:100vh;
}
/* Don't show outline around statuses if we're in
* mouse or touch mode (rather than keyboard) */
[data-whatinput="mouse"], [data-whatinput="touch"] {
.status__content:focus, .status:focus,
.status__wrapper:focus, .status__content__text:focus {
outline: none;
}
}
/* Less emphatic show more */
.status__content__read-more-button {
font-size: 14px;
color: $dark-text-color;
.status__prepend-icon {
padding-right: 4px;
}
}
/* Show a little arrowey thing after the time in a
* status to signal that you can click it to see
* a detailed view */
.status time:after,
.detailed-status__datetime span:after {
font: normal normal normal 14px/1 FontAwesome;
content: "\00a0\00a0\f08e";
}
/* Don't display the elephant mascot (we have our
* own, thanks) */
.drawer__inner__mastodon {
display: none;
}
/* Let the compose area/drawer be short, but
* expand if necessary */
.drawer .drawer__inner {
overflow: visible;
height:inherit;
background-image: none;
}
.drawer__pager {
overflow-y:auto;
}
/* Use display: none instead of visibility:hidden
* to hide the suggested follows list on non-mobile */
@media screen and (min-width: 630px) {
.search-results .trends {
display:none;
}
}
@import 'fullwidth-media';

View File

@ -0,0 +1,952 @@
$success-green: #B64579; // Padua
$ui-base-color: #f7e8ed; // "darkest"
$ui-base-alt: #f9f2f5;
$ui-base-lighter-color: darken($ui-base-color, 40%); // Lighter darkest
$ui-secondary-color: #ead0d6; // "lightest"
$ui-primary-color: #bf5677; // "lighter"
$ui-highlight-color: #bf5677; // "vibrant"
$primary-text-color: #382b32;
$dark-text-color: #ca748f;
$secondary-text-color: #382b32;
$header-color: $ui-primary-color;
$header-text-color: #fff;
$icon-button-inactive-color: lighten(desaturate($ui-base-lighter-color, 20%), 20%);
$action-button-color: $icon-button-inactive-color;
$about-page-text: $primary-text-color;
@import 'cybre-base';
$gold-star: #dd9d08;
/* cybre-specific additions */
.column .static-content.getting-started {
background-image: url('../images/logo-cybre-light.png');
background-size:auto 50%;
background-position: 50% 75%;
background-repeat:no-repeat;
}
.ui, body {
background: $ui-base-color url('../images/background-cybre-light.png');
}
.drawer__inner__mastodon {
display: none;
}
.landing-page .header-wrapper {
background-image:url('../images/header-cybre-alt.jpg');
background-size:cover;
background-position:50% 50%;
}
.landing-page.alternative .header {
background-image:url('../images/header-cybre-colour.jpg');
background-repeat: repeat-x;
background-size:contain;
height:45vh;
width: 100%;
position:absolute;
z-index: 1;
text-align:center;
display: unset!important;
}
.landing-page.alternative .header img {
margin: auto;
max-height:45vh;
}
.landing-page.alternative .grid {
position: relative;
z-index:2;
margin-top:15vh;
}
.landing-page.alternative .landing-page__hero img {
visibility: hidden;
max-height:170px;
}
.landing-page.alternative .landing-page__forms {
height:auto;
}
.landing-page.alternative .column-1 {
display:flex;
align-items:flex-end;
}
.landing-page.alternative .column {
max-height:initial;
}
.landing-page.alternative .row__mascot {
.floats {
position:absolute;
img {
width:100%;
height:100%;
}
transition: all 0.1s linear;
animation-name: floating;
animation-iteration-count: infinite;
animation-direction: alternate;
animation-timing-function: ease-in-out;
}
.float-1 {
width:50px;
height:50px;
bottom:60px;
left:110px;
animation-duration: 3s;
}
.float-2 {
width:130px;
height:130px;
left:85px;
bottom: -60px;
animation-duration: 3.5s;
animation-delay: 0.2s;
}
.float-3 {
width:100px;
height:100px;
right: 50;
top: -10px;
animation-duration: 4s;
animation-delay: 0.5s;
}
}
/* about.scss */
.landing-page {
h1 {
color: $about-page-text;
small {
color: lighten($about-page-text, 10%);
}
}
p, li {
color: $about-page-text;
}
.header-wrapper {
padding-top:0px;
background-size:cover;
background-position:50% 55%;
}
.header-wrapper {
.mascot {
width:500px;
bottom:-52px;
left:-120px;
}
}
.container.links {
background-color: $ui-base-color;
border-top: 5px solid $ui-primary-color;
width:100%;
max-width:100%;
padding:0px calc(50% - 400px);
a {
&:hover {
color: lighten($ui-primary-color, 10%);
}
}
}
.container.hero {
.floats {
display:none;
}
.closed-registrations-message, form {
border-top: 50px solid #5f4770;
-webkit-box-shadow: 0 0 6px rgba(0,0,0,.1);
box-shadow: 0 0 6px rgba(0,0,0,.1);
&:before {
font-size: 16px;
font-family:inherit;
line-height:inherit;
font-weight:normal;
color:white;
position:absolute;
top:-35px;
}
}
.closed-registrations-message:before {
content: "Registrations closed";
}
form:before {
content: "Register now";
}
}
#mastodon-timeline {
.column-header {
color:white;
}
}
}
.features-list__row {
.text {
color: $about-page-text;
}
}
.information-board {
.panel {
.panel-header {
color: $primary-text-color;
border-bottom: 1px solid lighten($ui-secondary-color, 4%);
a,
span {
font-weight: 400;
color: lighten($ui-primary-color, 4%);
}
}
}
}
/* components.scss */
.onboarding-modal__page {
p {
color: $primary-text-color;
}
}
.column-header {
background: $header-color;
color: $header-text-color;
border-top-left-radius: 3px;
border-top-right-radius: 3px;
box-shadow: 0px 0px 3px rgba(0,0,0,0.3);
}
.column-header__button {
background: $header-color;
color: $header-text-color;
border-top-right-radius: 3px;
&:hover {
color: darken($ui-base-color, 10%);
}
&.active {
color: $primary-text-color;
background: darken($ui-base-color, 5%);
&:hover {
background: darken($ui-base-color, 5%);
}
}
}
.status-card, .status-card.compact {
border-color: $ui-highlight-color;
}
// selectivity -- needs to override .column-header > button
.column-header .column-header__back-button {
background: $header-color;
color:$header-text-color;
}
.column-back-button {
background: $header-color;
color:$header-text-color;
}
.column-header__collapsible-inner {
background: darken($ui-base-alt, 2%);
}
.empty-column-indicator,
.error-column {
color: darken($ui-base-lighter-color, 15%);
}
.compose-form {
.autosuggest-textarea__textarea,
.spoiler-input__input {
color: $primary-text-color;
border: 1px solid $ui-primary-color;
}
.autosuggest-textarea__textarea {
border-bottom-width:0px;
}
.compose-form__modifiers {
border: 1px solid $ui-primary-color;
border-top-width:0px;
}
.compose-form__buttons button.active:last-child {
border-radius:3px;
background: $ui-base-color;
color: $ui-primary-color;
}
.compose-form__buttons-wrapper {
background-color:$ui-primary-color;
}
.icon-button.inverted {
color:white;
&:hover {
color:$ui-secondary-color;
}
}
}
button.icon-button {
&.disabled {
}
}
.icon-button {
&.inverted {
color: darken($ui-base-lighter-color, 10%);
}
&.overlayed {
background: rgba($base-overlay-background, 0.2);
color: rgba($white, 0.7);
&:hover {
background: rgba($base-overlay-background, 0.4);
}
}
&.disabled {
color: desaturate($icon-button-inactive-color, 5%);
&:hover,
&:active,
&:focus {
color: desaturate($icon-button-inactive-color, 5%);
}
}
color: $icon-button-inactive-color;
&:hover,
&:active,
&:focus {
color: darken($icon-button-inactive-color, 5%);
}
}
.icon-button.star-icon,
.icon-button.star-icon:active {
background:transparent;
border:none;
}
.icon-button.star-icon.active {
color: $gold-star;
&:active, &:hover, &:focus {
color: $gold-star;
}
}
.text-icon-button {
color: $white;
&.active {
background: $ui-base-color;
color: $ui-primary-color;
}
&:focus, &:hover {
color: darken($ui-base-color, 3%);
}
}
.status.status-direct {
background: darken($ui-base-alt, 5%);
.icon-button.disabled {
color: lighten($ui-base-lighter-color, 10%);
}
}
.account__header, .account-card {
& > div {
background: rgba(lighten($ui-base-color, 4%), 0.6);
}
.account__header__content {
color: $primary-text-color;
}
.detailed-status__display-name .display-name strong {
color: $ui-highlight-color;
}
.icon-button {
&, &:hover {
color:desaturate($ui-base-lighter-color, 20%);
}
&.active {
&, &:hover {
color:$ui-base-lighter-color;
}
}
}
}
.account__section-headline a {
&.active {
color: $primary-text-color;
&::after {
border-bottom-color: $ui-base-alt;
}
&::after {
border-bottom-color: $ui-base-alt;
}
}
}
.privacy-dropdown.active .privacy-dropdown__value.active .icon-button {
color: $ui-primary-color;
}
.privacy-dropdown__option {
color: $primary-text-color;
strong {
color: $primary-text-color;
}
&:hover,
&.active {
color: $white;
.privacy-dropdown__option__content {
color: $white;
strong {
color: $white;
}
}
}
}
.emoji-picker-dropdown__menu {
.emoji-search-wrapper {
border-color: darken($ui-base-color, 10%);
}
.emoji-search {
background: darken($ui-base-color, 5%);
border-color: darken($ui-base-color, 10%);
}
.emoji-mart {
color: $ui-primary-color;
}
}
.search-popout {
background: $ui-base-color;
color: $ui-primary-color;
h4 {
color: $ui-primary-color;
}
em {
color: $ui-highlight-color;
}
}
.search__icon .fa.active {
opacity:1.0;
}
.search-results__hashtag {
color: darken($ui-primary-color, 10%);
&:hover {
color: lighten($ui-primary-color, 5%);
}
}
.static-content {
/*color: $primary-text-color;*/
}
#Getting-started {
background: $ui-primary-color;
border-bottom:0px;
color:white;
}
.getting-started {
p {
color: $primary-text-color;
}
a {
color: darken($ui-base-lighter-color, 10%);
}
}
.getting-started__wrapper {
flex: 0 0.5 auto;
}
.getting-started {
.column-link {
background: lighten($ui-primary-color, 5%);
color:$white;
&:hover {
background: lighten($ui-primary-color, 10%);
}
}
}
.column-link__badge {
background: saturate(darken($ui-primary-color, 5%), 5%);
}
.column-subheading {
background: darken($ui-primary-color, 5%);
color:$white;
}
.media-spoiler,
.video-player__spoiler.active {
color: $white;
&:hover {
color: darken($white, 5%);
}
}
.status {
border-bottom: 1px solid $ui-secondary-color;
}
.status__relative-time, .status__display-name {
color: darken($ui-base-color, 40%);
}
.status__content {
.status__content__spoiler-link {
background: $ui-base-lighter-color;
&:hover {
background: lighten($ui-base-lighter-color, 5%);
}
}
}
.muted .status__content p {
color: $icon-button-inactive-color;
}
.dropdown-menu__item {
& > a {
color: $primary-text-color;
&:hover, &:active, &:focus {
color: $white;
}
}
}
.dropdown--active .dropdown__content {
& > ul {
background: $ui-base-color;
box-shadow: 0 0 5px rgba($base-shadow-color, 0.2);
& > li > a {
background: $ui-base-color;
color: $primary-text-color;
&:hover {
background: $ui-highlight-color;
color: $ui-base-color;
}
}
}
}
.boost-modal,
.confirmation-modal,
.report-modal,
.actions-modal,
.mute-modal
{
color: $primary-text-color;
}
.boost-modal__action-bar,
.confirmation-modal__action-bar,
.mute-modal__action-bar,
.report-modal__action-bar,
.mute-modal__action-bar {
& > div {
color: $ui-primary-color;
}
}
.actions-modal
{
ul {
li:not(:empty) {
a {
color: $primary-text-color;
button {
}
&.active, &:hover, &:active, &:focus {
color: $white;
button {
color: $white;
}
}
}
}
}
}
.react-toggle-track {
background-color: $icon-button-inactive-color;
}
.report-modal__comment .setting-text {
color: $primary-text-color;
border-bottom-color: lighten($ui-primary-color, 10%);
&:focus, &:active {
color: $primary-text-color;
}
}
.status.light {
.status__content {
color: $primary-text-color;
}
.display-name strong {
color: $primary-text-color;
}
}
.reply-indicator__content a {
color: lighten($ui-highlight-color, 30%);
}
.status__content
{
a {
color: $ui-highlight-color;
&:hover {
.fa {
color: darken($ui-base-color, 40%);
}
}
}
}
.detailed-status__display-name {
color: $ui-base-lighter-color;
}
.drawer .drawer__inner {
overflow: visible;
height:inherit;
background:$ui-base-alt;
}
.search__icon .fa {
color: $ui-highlight-color;
}
.drawer__pager {
overflow-y:auto;
}
.drawer .drawer__header {
background: $ui-base-color;
border-radius:3px;
}
.onboarding-modal__page h1 {
background-color: darken($ui-primary-color, 5%);
}
.poll__text input[type="text"],
.compose-form__poll-wrapper select {
color: $primary-text-color;
}
.compose-form__poll-wrapper .button.button-secondary {
color: $ui-highlight-color;
}
/* forms.scss */
.block-button, .button, button {
background-color: $ui-primary-color;
color: $white;
&.button-alternative {
color: $ui-base-color;
}
&.logo-button {
color: $white;
svg path:first-child {
fill: $white;
}
}
}
.simple_form {
p.hint {
color: $primary-text-color;
}
.block-button, .button, button {
background-color: $ui-primary-color;
color: $white;
&:hover {
background-color: lighten($ui-primary-color, 5%);
}
&:active,
&:focus {
background-color: darken($ui-primary-color, 5%);
}
}
}
/* admin.scss */
.table > thead > tr > th {
border-bottom-color: $ui-secondary-color;
}
.simple_form h4 {
border-bottom: 1px solid $ui-highlight-color;
}
.admin-wrapper {
.content {
h2, p.hint, h4, h6 {
color: $primary-text-color;
}
.muted-hint {
color: $primary-text-color;
}
}
.sidebar {
.logo {
-webkit-filter: invert(100%);
filter: invert(100%);
}
ul {
ul {
a {
&.selected {
background-color: $ui-primary-color;
color: $white;
&:hover {
background-color: lighten($ui-primary-color, 10%);
}
}
}
}
a {
&.selected {
background-color: $ui-primary-color;
color: $white;
&:hover {
background-color: lighten($ui-primary-color, 10%);
}
}
}
}
}
}
.pagination .current {
color: $ui-primary-color;
}
.report-accounts__item > strong {
color: $primary-text-color;
}
.admin-wrapper .content {
& > p {
color: $primary-text-color;
}
hr {
border-color: $ui-highlight-color;
}
}
/* accounts.scss */
.card {
.name {
color: $white;
}
.counter {
.counter-number {
color: $white;
}
}
}
/* stream_entries.scss */
.activity-stream {
.entry {
}
.status.light {
.display-name {
strong {
color: $primary-text-color;
}
}
.status__content {
color: $primary-text-color;
}
}
.detailed-status.light {
.detailed-status__display-name {
.display-name {
strong {
color: $primary-text-color;
}
}
}
.status__content {
color: $primary-text-color;
}
.status-card,
.status-card__title,
.status-card__description {
color: $primary-text-color;
}
}
}
/* accounts.scss */
.card {
.name {
color: darken($ui-primary-color, 15%);
}
.counter {
.counter-number {
color: darken($ui-primary-color, 15%);
}
border-color: $ui-primary-color;
}
}
.activity-stream-tabs {
a {
color: lighten($ui-primary-color, 10%);
&.active {
color: darken($ui-primary-color, 10%);
}
}
}
/* uncategorized */
@media screen and (min-width: 1300px) {
.column {
flex-grow: 1 !important;
max-width: 400px;
}
.drawer {
width: 17%;
max-width: 400px;
min-width: 330px;
}
}
.status time:after,
.detailed-status__datetime span:after {
font: normal normal normal 14px/1 FontAwesome;
content: "\00a0\00a0\f08e";
}
.column {
max-height:100vh;
& > .scrollable {
background-color: $ui-base-alt;
}
}
.empty-column-indicator, .error-column {
background-color: $ui-base-alt;
}
.actions .button.button-alternative {
background: $ui-highlight-color;
color: $white;
&:active,
&:focus,
&:hover {
background-color: lighten($ui-highlight-color, 4%);
}
}
.public-layout .header {
background: $ui-highlight-color;
color: $white;
}
.public-layout .public-account-header__tabs__name h1 {
color: $white;
small {
color: $white;
}
}
.public-layout .header .brand:hover,
.public-layout .header .brand:focus,
.public-layout .header .brand:active {
background: lighten($ui-highlight-color, 5%);
}
.public-layout .container:last-child {
background:$ui-highlight-color;
padding-left: 100px;
padding-right: 100px;
border-radius: 4px;
h4 {
color: white;
}
}
.modal-layout, .modal-layout__mastodon > * {
background: none;
}
.dashboard__widgets a:not(.name-tag) {
color: $primary-text-color;
}

View File

@ -0,0 +1,272 @@
$ui-base-color: #181818; // darkest
$ui-highlight-color: #1ea21e; // vibrant
$ui-secondary-color: #E4F2E4; // lightest
$ui-primary-color: #E4F2E4; // lighter
$ui-primary-color-alt: #a0b49c; // darker, for external pages
$about-page-text: lighten($ui-base-color, 50%);
@import 'cybre-base';
@keyframes floating {
from {
transform: translate(0, 0);
}
65% {
transform: translate(0, 4px);
}
to {
transform: translate(0, -0);
}
}
body, body.about-body {
background: $ui-base-color url('../images/background-cybre.png');
}
body.about-body {
// basics.scss &.about-body
background: darken($ui-base-color, 8%) url('../images/background-cybre.png');
background-position-y: 200px;
background-position-x: center;
}
.about-body .mascot {
display: none;
}
.muted {
.status__content p, .status__content a {
color: lighten($ui-base-color, 35%);
}
.status__display-name strong {
color: lighten($ui-base-color, 35%);
}
}
.compose-form__buttons button.active:last-child {
color:$ui-secondary-color;
background-color: $ui-highlight-color;
border-radius:3px;
}
.screenshot-with-signup {
min-height:300px;
}
.container.hero .closed-registrations-message .clock {
font-size: 150%;
margin: 1em auto;
}
.column .static-content.getting-started {
background-image: url('../images/logo-cybre.png'), url('../images/background-cybre.png');
background-size:auto 50%, cover;
background-position: 50% 75%, center center;
background-repeat:no-repeat, no-repeat;
}
.columns-area {
background: $ui-base-color url('../images/background-cybre.png');
}
.actions .button.button-alternative {
background: $ui-highlight-color;
color: $ui-primary-color;
&:active,
&:focus,
&:hover {
background-color: lighten($ui-highlight-color, 4%);
}
}
@media screen and (max-width: 1280px) {
.landing-page .container.links {
top: -15px;
}
}
.landing-page.alternative .header {
background-image:url('../images/header-cybre-colour.jpg');
background-repeat: repeat-x;
background-size:contain;
height:45vh;
width: 100%;
position:absolute;
z-index: 1;
text-align:center;
display: unset!important;
}
.landing-page.alternative .header img {
margin: auto;
max-height:45vh;
}
.landing-page.alternative .grid {
position: relative;
z-index:2;
margin-top:15vh;
}
.landing-page.alternative .landing-page__hero img {
visibility: hidden;
max-height:170px;
}
.landing-page.alternative .landing-page__forms {
height:auto;
}
.landing-page.alternative .column-1 {
display:flex;
align-items:flex-end;
}
.landing-page.alternative .column {
max-height:initial;
}
.landing-page.alternative .row__mascot {
.floats {
position:absolute;
img {
width:100%;
height:100%;
}
transition: all 0.1s linear;
animation-name: floating;
animation-iteration-count: infinite;
animation-direction: alternate;
animation-timing-function: ease-in-out;
}
.float-1 {
width:50px;
height:50px;
bottom:60px;
left:110px;
animation-duration: 3s;
}
.float-2 {
width:130px;
height:130px;
left:85px;
bottom: -60px;
animation-duration: 3.5s;
animation-delay: 0.2s;
}
.float-3 {
width:100px;
height:100px;
right: 50;
top: -10px;
animation-duration: 4s;
animation-delay: 0.5s;
}
}
.activity-stream {
.status.light {
.status__header .status__meta .status__relative-time {
color: $ui-primary-color-alt;
}
.display-name span {
color: $ui-primary-color-alt;
}
.status__content {
a.status__content__spoiler-link {
background: $ui-primary-color-alt;
&:hover {
background: lighten($ui-primary-color-alt, 8%);
}
}
}
}
.detailed-status.light {
.detailed-status__display-name .display-name span {
color: $ui-primary-color-alt;
}
.status__content a.status__content__spoiler-link {
background: $ui-primary-color-alt;
&:hover {
background: lighten($ui-primary-color-alt, 8%);
}
}
.detailed-status__meta {
color: $ui-primary-color-alt;
}
}
.media-spoiler {
background: $ui-primary-color-alt;
&:hover {
background: darken($ui-primary-color-alt, 5%);
}
}
.pre-header {
color: $ui-primary-color-alt;
.status__display-name.muted strong {
color: $ui-primary-color-alt;
}
}
}
.embed .activity-stream .entry .detailed-status.light .button.button-secondary.logo-button {
color: $ui-primary-color-alt;
svg {
path:first-child {
fill: $ui-primary-color-alt;
}
}
&:active,
&:focus,
&:hover {
svg path:first-child {
fill: lighten($ui-primary-color-alt, 4%);
}
}
}
.emoji-mart-search {
background: $simple-background-color;
input {
color: $ui-primary-color-alt;
border: 1px solid $ui-primary-color-alt;
}
}
.emoji-mart-anchor {
color: $ui-primary-color-alt;
&:hover {
color: darken($ui-primary-color-alt, 8%);
}
}
.search-popout {
background: $ui-base-color;
color: $ui-primary-color;
h4 {
color: $ui-primary-color;
}
em {
color: $ui-highlight-color;
}
}

View File

@ -0,0 +1,48 @@
.detailed-status > .media-spoiler,
.status > .media-spoiler,
.status .video-player,
.media-gallery,
.status .status-card.interactive {
margin-top: 20px;
margin-left: -68px;
width: calc(100% + 80px);
}
.detailed-status > .media-spoiler,
.status > .media-spoiler,
.video-player {
max-width: none;
}
/* If there's no status text, add an extra margin on top */
.status .status__info + .media-gallery,
.status .status__info + .media-spoiler,
.status .status__info + .video-player,
.status .status__info + .status-card {
margin-top: 40px;
}
.status__video-player-video {
transform: unset;
top: unset;
}
.detailed-status .media-gallery {
margin-left: -10px;
width: calc(100% + 22px);
}
.public-layout .status {
.status__content {
min-height: 15px;
}
& > .media-spoiler,
.video-player,
.media-gallery,
.status-card {
margin-top: 20px;
width: calc(100% + 94px);
margin-left: -78px;
}
}

View File

@ -162,7 +162,7 @@
.actions-modal ul li:not(:empty) a:focus button,
.actions-modal ul li:not(:empty) a:hover,
.actions-modal ul li:not(:empty) a:hover button,
.admin-wrapper .sidebar ul ul a.selected,
.admin-wrapper .sidebar ul li a.selected,
.simple_form .block-button,
.simple_form .button,
.simple_form button {
@ -230,6 +230,7 @@
.empty-column-indicator,
.error-column {
color: $primary-text-color;
background: $white;
}
// Change the default colors used on some parts of the profile pages

View File

@ -193,7 +193,6 @@ $small-breakpoint: 960px;
}
strong {
font-family: $font-display, sans-serif;
font-weight: 500;
font-size: 32px;
line-height: 48px;
@ -281,6 +280,168 @@ $small-breakpoint: 960px;
}
.landing-page {
.grid {
display: grid;
grid-gap: 10px;
grid-template-columns: 1fr 2fr;
grid-auto-columns: 25%;
grid-auto-rows: max-content;
.column-0 {
display: none;
}
.column-1 {
grid-column: 1;
grid-row: 1;
}
.column-2 {
grid-column: 2;
grid-row: 1;
}
.column-3 {
grid-column: 3;
grid-row: 1 / 3;
}
.column-4 {
grid-column: 1 / 3;
grid-row: 2;
}
}
@media screen and (max-width: $small-breakpoint) {
.grid {
grid-template-columns: 40% 60%;
.column-0 {
display: none;
}
.column-1 {
grid-column: 1;
grid-row: 1;
&.non-preview .landing-page__forms {
height: 100%;
}
}
.column-2 {
grid-column: 2;
grid-row: 1 / 3;
&.non-preview {
grid-column: 2;
grid-row: 1;
}
}
.column-3 {
grid-column: 1;
grid-row: 2 / 4;
}
.column-4 {
grid-column: 2;
grid-row: 3;
&.non-preview {
grid-column: 1 / 3;
grid-row: 2;
}
}
}
}
@media screen and (max-width: $column-breakpoint) {
.grid {
grid-template-columns: 100%;
.column-0 {
display: block;
grid-column: 1;
grid-row: 1;
}
.column-1 {
grid-column: 1;
grid-row: 3;
.brand {
display: none;
}
}
.column-2 {
grid-column: 1;
grid-row: 2;
.landing-page__logo,
.landing-page__call-to-action {
display: none;
}
&.non-preview {
grid-column: 1;
grid-row: 2;
}
}
.column-3 {
grid-column: 1;
grid-row: 5;
}
.column-4 {
grid-column: 1;
grid-row: 4;
&.non-preview {
grid-column: 1;
grid-row: 4;
}
}
}
}
.column-flex {
display: flex;
flex-direction: column;
}
.separator-or {
position: relative;
margin: 40px 0;
text-align: center;
&::before {
content: "";
display: block;
width: 100%;
height: 0;
border-bottom: 1px solid rgba($ui-base-lighter-color, .6);
position: absolute;
top: 50%;
left: 0;
}
span {
display: inline-block;
background: $ui-base-color;
font-size: 12px;
font-weight: 500;
color: $darker-text-color;
text-transform: uppercase;
position: relative;
z-index: 1;
padding: 0 8px;
cursor: default;
}
}
p,
li {
font-family: $font-sans-serif, sans-serif;
@ -297,6 +458,28 @@ $small-breakpoint: 960px;
}
}
.closed-registrations-message {
margin-top: 20px;
&,
p {
text-align: center;
font-size: 12px;
line-height: 18px;
color: $darker-text-color;
margin-bottom: 0;
a {
color: $highlight-text-color;
text-decoration: underline;
}
}
p:last-child {
margin-bottom: 0;
}
}
em {
display: inline;
margin: 0;
@ -410,6 +593,187 @@ $small-breakpoint: 960px;
}
}
.container-alt {
width: 100%;
box-sizing: border-box;
max-width: 800px;
margin: 0 auto;
word-wrap: break-word;
}
.header-wrapper {
padding-top: 15px;
background: $ui-base-color;
background: linear-gradient(150deg, lighten($ui-base-color, 8%), $ui-base-color);
position: relative;
&.compact {
background: $ui-base-color;
padding-bottom: 15px;
.hero .heading {
padding-bottom: 20px;
font-family: $font-sans-serif, sans-serif;
font-size: 16px;
font-weight: 400;
font-size: 16px;
line-height: 30px;
color: $darker-text-color;
a {
color: $highlight-text-color;
text-decoration: underline;
}
}
}
}
.brand {
a {
padding-left: 0;
padding-right: 0;
color: $white;
}
img {
height: 32px;
position: relative;
top: 4px;
left: -10px;
}
}
.header {
line-height: 30px;
overflow: hidden;
.container-alt {
display: flex;
justify-content: space-between;
}
.links {
position: relative;
z-index: 4;
a {
display: flex;
justify-content: center;
align-items: center;
color: $darker-text-color;
text-decoration: none;
padding: 12px 16px;
line-height: 32px;
font-family: $font-display, sans-serif;
font-weight: 500;
font-size: 14px;
&:hover {
color: $secondary-text-color;
}
}
ul {
list-style: none;
margin: 0;
li {
display: inline-block;
vertical-align: bottom;
margin: 0;
&:first-child a {
padding-left: 0;
}
&:last-child a {
padding-right: 0;
}
}
}
}
.hero {
margin-top: 50px;
align-items: center;
position: relative;
.heading {
position: relative;
z-index: 4;
padding-bottom: 150px;
}
.simple_form,
.closed-registrations-message {
background: darken($ui-base-color, 4%);
width: 280px;
padding: 15px 20px;
border-radius: 4px 4px 0 0;
line-height: initial;
position: relative;
z-index: 4;
.actions {
margin-bottom: 0;
button,
.button,
.block-button {
margin-bottom: 0;
}
}
}
.closed-registrations-message {
min-height: 330px;
display: flex;
flex-direction: column;
justify-content: space-between;
}
}
}
.about-short {
background: darken($ui-base-color, 4%);
padding: 50px 0 30px;
font-family: $font-sans-serif, sans-serif;
font-size: 16px;
font-weight: 400;
font-size: 16px;
line-height: 30px;
color: $darker-text-color;
a {
color: $highlight-text-color;
text-decoration: underline;
}
}
&.alternative {
padding: 10px 0;
.brand {
text-align: center;
padding: 30px 0;
margin-bottom: 10px;
img {
position: static;
padding: 10px 0;
}
@media screen and (max-width: $small-breakpoint) {
padding: 15px 0;
}
@media screen and (max-width: $column-breakpoint) {
padding: 0;
margin-bottom: -10px;
}
}
}
&__information,
&__forms {
padding: 20px;
@ -477,6 +841,14 @@ $small-breakpoint: 960px;
strong {
font-weight: 500;
display: inline;
margin: 0;
padding: 0;
font-weight: 700;
background: transparent;
font-family: inherit;
font-size: inherit;
line-height: inherit;
color: lighten($darker-text-color, 10%);
}
@ -603,7 +975,215 @@ $small-breakpoint: 960px;
}
}
&__forms {
height: 100%;
@media screen and (max-width: $small-breakpoint) {
height: auto;
}
@media screen and (max-width: $column-breakpoint) {
background: transparent;
box-shadow: none;
padding: 0 20px;
margin-top: 30px;
margin-bottom: 40px;
.separator-or {
span {
background: darken($ui-base-color, 8%);
}
}
}
hr {
margin: 40px 0;
}
.button {
display: block;
}
.subtle-hint a {
text-decoration: none;
&:hover,
&:focus,
&:active {
text-decoration: underline;
}
}
}
#mastodon-timeline {
display: flex;
-webkit-overflow-scrolling: touch;
-ms-overflow-style: -ms-autohiding-scrollbar;
font-family: $font-sans-serif, sans-serif;
font-size: 13px;
line-height: 18px;
font-weight: 400;
color: $primary-text-color;
width: 100%;
flex: 1 1 auto;
overflow: hidden;
height: 100%;
.column-header {
color: inherit;
font-family: inherit;
font-size: 16px;
line-height: inherit;
font-weight: inherit;
margin: 0;
padding: 0;
}
.column {
padding: 0;
border-radius: 4px;
overflow: hidden;
width: 100%;
}
.scrollable {
height: 400px;
}
p {
font-size: inherit;
line-height: inherit;
font-weight: inherit;
color: $primary-text-color;
margin-bottom: 20px;
&:last-child {
margin-bottom: 0;
}
a {
color: $secondary-text-color;
text-decoration: none;
}
}
.attachment-list__list {
margin-left: 0;
list-style: none;
li {
font-size: inherit;
line-height: inherit;
font-weight: inherit;
margin-bottom: 0;
a {
color: $dark-text-color;
text-decoration: none;
&:hover {
text-decoration: underline;
}
}
}
}
@media screen and (max-width: $column-breakpoint) {
display: none;
}
}
&__features {
& > p {
padding-right: 60px;
}
.features-list {
margin: 40px 0;
margin-top: 30px;
}
&__action {
text-align: center;
}
}
.features-list {
.features-list__row {
display: flex;
padding: 10px 0;
justify-content: space-between;
.visual {
flex: 0 0 auto;
display: flex;
align-items: center;
margin-left: 15px;
.fa {
display: block;
color: $darker-text-color;
font-size: 48px;
}
}
.text {
font-size: 16px;
line-height: 30px;
color: $darker-text-color;
h6 {
font-size: inherit;
line-height: inherit;
margin-bottom: 0;
}
}
}
@media screen and (min-width: $small-breakpoint) {
display: grid;
grid-gap: 30px;
grid-template-columns: 1fr 1fr;
grid-auto-columns: 50%;
grid-auto-rows: max-content;
}
}
.footer-links {
padding-bottom: 50px;
text-align: right;
color: $dark-text-color;
p {
font-size: 14px;
}
a {
color: inherit;
text-decoration: underline;
}
}
&__footer {
margin-top: 10px;
text-align: center;
color: $dark-text-color;
p {
font-size: 14px;
a {
color: inherit;
text-decoration: underline;
}
}
}
@media screen and (max-width: 840px) {
.container-alt {
padding: 0 20px;
}
.information-board {
.container-alt {
padding-right: 20px;
@ -639,217 +1219,109 @@ $small-breakpoint: 960px;
.features .container-alt {
display: block;
}
.header {
.links {
padding-top: 15px;
background: darken($ui-base-color, 4%);
a {
padding: 12px 8px;
}
.nav {
display: flex;
flex-flow: row wrap;
justify-content: space-around;
}
.brand img {
left: 0;
top: 0;
}
}
.hero {
margin-top: 30px;
padding: 0;
.heading {
padding: 30px 20px;
text-align: center;
}
.simple_form,
.closed-registrations-message {
background: darken($ui-base-color, 8%);
width: 100%;
border-radius: 0;
box-sizing: border-box;
}
}
}
}
.cta {
margin: 20px;
}
}
.landing {
margin-bottom: 100px;
@media screen and (max-width: 738px) {
margin-bottom: 0;
}
&__brand {
display: flex;
justify-content: center;
align-items: center;
padding: 50px;
img {
height: 52px;
}
@media screen and (max-width: $no-gap-breakpoint) {
&.tag-page {
@media screen and (max-width: $column-breakpoint) {
padding: 0;
margin-bottom: 30px;
}
}
.directory {
margin-top: 30px;
background: transparent;
box-shadow: none;
border-radius: 0;
}
.hero-widget {
margin-top: 30px;
margin-bottom: 0;
h4 {
padding: 10px;
text-transform: uppercase;
font-weight: 700;
font-size: 13px;
color: $darker-text-color;
}
&__text {
border-radius: 0;
padding-bottom: 0;
}
&__footer {
background: $ui-base-color;
padding: 10px;
border-radius: 0 0 4px 4px;
display: flex;
&__column {
flex: 1 1 50%;
.container {
padding: 0;
}
}
.account {
padding: 10px 0;
border-bottom: 0;
.account__display-name {
#mastodon-timeline {
display: flex;
align-items: center;
}
.account__avatar {
width: 44px;
height: 44px;
background-size: 44px 44px;
height: 100vh;
border-radius: 0;
}
}
&__counter {
padding: 10px;
strong {
font-family: $font-display, sans-serif;
font-size: 15px;
font-weight: 700;
display: block;
.grid {
@media screen and (min-width: $small-breakpoint) {
grid-template-columns: 33% 67%;
}
span {
font-size: 14px;
color: $darker-text-color;
}
}
}
.simple_form .user_agreement .label_input > label {
font-weight: 400;
color: $darker-text-color;
}
.simple_form p.lead {
color: $darker-text-color;
font-size: 15px;
line-height: 20px;
font-weight: 400;
margin-bottom: 25px;
}
&__grid {
max-width: 960px;
margin: 0 auto;
display: grid;
grid-template-columns: minmax(0, 50%) minmax(0, 50%);
grid-gap: 30px;
@media screen and (max-width: 738px) {
grid-template-columns: minmax(0, 100%);
grid-gap: 10px;
&__column-login {
.column-2 {
grid-column: 2;
grid-row: 1;
display: flex;
flex-direction: column;
.box-widget {
order: 2;
flex: 0 0 auto;
}
.hero-widget {
margin-top: 0;
margin-bottom: 10px;
order: 1;
flex: 0 0 auto;
}
}
&__column-registration {
grid-row: 2;
}
.directory {
margin-top: 10px;
}
}
@media screen and (max-width: $no-gap-breakpoint) {
grid-gap: 0;
.brand {
text-align: unset;
padding: 0;
.hero-widget {
display: block;
margin-bottom: 0;
box-shadow: none;
img {
height: 48px;
width: auto;
}
}
&__img,
&__img img,
&__footer {
border-radius: 0;
.cta {
margin: 0;
.button {
margin-right: 4px;
}
}
@media screen and (max-width: $column-breakpoint) {
.grid {
grid-gap: 0;
.column-1 {
grid-column: 1;
grid-row: 1;
}
}
.hero-widget,
.box-widget,
.directory__tag {
border-bottom: 1px solid lighten($ui-base-color, 8%);
}
.directory {
margin-top: 0;
&__tag {
margin-bottom: 0;
& > a,
& > div {
border-radius: 0;
box-shadow: none;
}
&:last-child {
border-bottom: 0;
}
.column-2 {
display: none;
}
}
}
}
}
.brand {
position: relative;
text-decoration: none;
}
.brand__tagline {
display: block;
position: absolute;
bottom: -10px;
left: 50px;
width: 300px;
color: $ui-primary-color;
text-decoration: none;
font-size: 14px;
@media screen and (max-width: $no-gap-breakpoint) {
position: static;
width: auto;
margin-top: 20px;
color: $dark-text-color;
}
}

View File

@ -268,9 +268,34 @@
padding: 10px;
padding-top: 0;
.icon-button {
font-size: 14px;
font-weight: 500;
font-size: 14px;
font-weight: 500;
&.active {
color: $highlight-text-color;
}
input[type=checkbox] {
display: none;
}
.checkbox {
display: inline-block;
position: relative;
border: 1px solid $ui-primary-color;
box-sizing: border-box;
width: 18px;
height: 18px;
flex: 0 0 auto;
margin-right: 10px;
top: -1px;
border-radius: 4px;
vertical-align: middle;
&.active {
border-color: $highlight-text-color;
background: $highlight-text-color;
}
}
}
@ -1386,6 +1411,15 @@ a.account__display-name {
width: 48px;
}
.status__expand {
width: 68px;
position: absolute;
left: 0;
top: 0;
height: 100%;
cursor: pointer;
}
.muted {
.status__content p,
.status__content a {
@ -2533,10 +2567,6 @@ a.status-card {
width: 100%;
}
.status-card__image-image {
border-radius: 4px 4px 0 0;
}
.status-card__title {
white-space: inherit;
}
@ -2568,7 +2598,6 @@ a.status-card.compact:hover {
}
.status-card__image-image {
border-radius: 4px 0 0 4px;
display: block;
margin: 0;
width: 100%;
@ -4829,6 +4858,14 @@ a.status-card.compact:hover {
border-radius: 4px;
overflow: hidden;
margin: 2px;
&__icons {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
font-size: 24px;
}
}
.notification__filter-bar,

View File

@ -196,8 +196,6 @@
}
.container {
max-width: 960px;
@media screen and (max-width: $no-gap-breakpoint) {
padding: 0;
}
@ -231,6 +229,12 @@
min-height: 1px;
}
h2 {
font-size: 1rem;
align-items: center;
display: flex;
}
.nav-left {
display: flex;
align-items: stretch;

View File

@ -114,11 +114,14 @@
text-decoration: underline;
font-size: inherit;
&:hover,
&:focus,
&:active {
&:hover {
text-decoration: none;
}
&:active,
&:focus {
background-color: rgba($dark-text-color, .1);
}
}
.button {

File diff suppressed because it is too large Load Diff

View File

@ -90,7 +90,7 @@ class ActivityPub::Activity
crawl_links(status)
notify_about_reblog(status) if reblog_of_local_account?(status)
notify_about_mentions(status)
notify_about_mentions(status) unless spammy_mentions?(status)
# Only continue if the status is supposed to have arrived in real-time.
# Note that if @options[:override_timestamps] isn't set, the status
@ -105,6 +105,11 @@ class ActivityPub::Activity
status.reblog? && status.reblog.account.local?
end
def spammy_mentions?(status)
status.has_non_mention_links? &&
@account.followers.local.count == 0
end
def notify_about_reblog(status)
NotifyService.new.call(status.reblog.account, status)
end

View File

@ -187,7 +187,7 @@ class Formatter
end
def rewrite(text, entities)
chars = text.to_s.to_char_a
text = text.to_s
# Sort by start index
entities = entities.sort_by do |entity|
@ -199,12 +199,12 @@ class Formatter
last_index = entities.reduce(0) do |index, entity|
indices = entity.respond_to?(:indices) ? entity.indices : entity[:indices]
result << encode(chars[index...indices.first].join)
result << encode(text[index...indices.first])
result << yield(entity)
indices.last
end
result << encode(chars[last_index..-1].join)
result << encode(text[last_index..-1])
result.flatten.join
end
@ -231,23 +231,14 @@ class Formatter
# Note: I couldn't obtain list_slug with @user/list-name format
# for mention so this requires additional check
special = Extractor.extract_urls_with_indices(escaped, options).map do |extract|
# exactly one of :url, :hashtag, :screen_name, :cashtag keys is present
key = (extract.keys & [:url, :hashtag, :screen_name, :cashtag]).first
new_indices = [
old_to_new_index.find_index(extract[:indices].first),
old_to_new_index.find_index(extract[:indices].last),
]
has_prefix_char = [:hashtag, :screen_name, :cashtag].include?(key)
value_indices = [
new_indices.first + (has_prefix_char ? 1 : 0), # account for #, @ or $
new_indices.last - 1,
]
next extract.merge(
:indices => new_indices,
key => text[value_indices.first..value_indices.last]
indices: new_indices,
url: text[new_indices.first..new_indices.last - 1]
)
end
@ -269,8 +260,9 @@ class Formatter
def link_to_mention(entity, linkable_accounts)
acct = entity[:screen_name]
username, domain = acct.split('@')
return link_to_account(acct) unless linkable_accounts
return link_to_account(acct) unless linkable_accounts and domain != "twitter.com"
account = linkable_accounts.find { |item| TagManager.instance.same_acct?(item.acct, acct) }
account ? mention_html(account) : "@#{encode(acct)}"
@ -279,6 +271,10 @@ class Formatter
def link_to_account(acct)
username, domain = acct.split('@')
if domain == "twitter.com"
return mention_twitter_html(username)
end
domain = nil if TagManager.instance.local_domain?(domain)
account = EntityCache.instance.mention(username, domain)
@ -306,4 +302,8 @@ class Formatter
def mention_html(account)
"<span class=\"h-card\"><a href=\"#{encode(TagManager.instance.url_for(account))}\" class=\"u-url mention\">@<span>#{encode(account.username)}</span></a></span>"
end
def mention_twitter_html(username)
"<span class=\"h-card\"><a href=\"https://twitter.com/#{username}\" class=\"u-url mention\">@<span>#{username}@twitter.com</span></a></span>"
end
end

View File

@ -75,7 +75,8 @@ class Account < ApplicationRecord
validates_with UniqueUsernameValidator, if: -> { local? && will_save_change_to_username? }
validates_with UnreservedUsernameValidator, if: -> { local? && will_save_change_to_username? }
validates :display_name, length: { maximum: 30 }, if: -> { local? && will_save_change_to_display_name? }
validates :note, note_length: { maximum: 160 }, if: -> { local? && will_save_change_to_note? }
validates :note, note_length: { maximum: 413 }, if: -> { local? && will_save_change_to_note? }
validate :note_has_eight_newlines?, if: -> { local? && will_save_change_to_note? }
validates :fields, length: { maximum: 4 }, if: -> { local? && will_save_change_to_fields? }
scope :remote, -> { where.not(domain: nil) }
@ -299,10 +300,8 @@ class Account < ApplicationRecord
def save_with_optional_media!
save!
rescue ActiveRecord::RecordInvalid
self.avatar = nil
self.header = nil
self[:avatar_remote_url] = ''
self[:header_remote_url] = ''
self.avatar = nil if errors[:avatar].present?
self.header = nil if errors[:header].present?
save!
end
@ -326,6 +325,10 @@ class Account < ApplicationRecord
shared_inbox_url.presence || inbox_url
end
def note_has_eight_newlines?
errors.add(:note, 'Bio can\'t have more then 8 newlines') unless note.count("\n") <= 8
end
class Field < ActiveModelSerializers::Model
attributes :name, :value, :verified_at, :account, :errors

View File

@ -431,6 +431,14 @@ class Status < ApplicationRecord
end
end
def has_non_mention_links?
if local?
text.match? %r{https?://\w}
else
Nokogiri::HTML.fragment(text).css('a:not(.mention)').present?
end
end
private
def update_status_stat!(attrs)

View File

@ -114,6 +114,10 @@ class User < ApplicationRecord
end
def invited?
invite_id.present?
end
def valid_invitation?
invite_id.present? && invite.valid_for_use?
end
@ -274,7 +278,7 @@ class User < ApplicationRecord
private
def set_approved
self.approved = open_registrations? || invited? || external?
self.approved = open_registrations? || valid_invitation? || external?
end
def open_registrations?

View File

@ -8,6 +8,7 @@ class InstancePresenter
:site_description,
:site_extended_description,
:site_terms,
:open_registrations,
:closed_registrations_message,
to: Setting
)

View File

@ -18,7 +18,9 @@ class ReblogService < BaseService
return reblog unless reblog.nil?
reblog = account.statuses.create!(reblog: reblogged_status, text: '', visibility: options[:visibility] || account.user&.setting_default_privacy)
visibility = options[:visibility] || account.user&.setting_default_privacy
visibility = reblogged_status.visibility if reblogged_status.hidden?
reblog = account.statuses.create!(reblog: reblogged_status, text: '', visibility: visibility)
DistributionWorker.perform_async(reblog.id)
Pubsubhubbub::DistributionWorker.perform_async(reblog.stream_entry.id)

View File

@ -2,7 +2,7 @@
class BlacklistedEmailValidator < ActiveModel::Validator
def validate(user)
return if user.invited?
return if user.valid_invitation?
@email = user.email

View File

@ -1,7 +1,7 @@
# frozen_string_literal: true
class StatusLengthValidator < ActiveModel::Validator
MAX_CHARS = 500
MAX_CHARS = 512
def validate(status)
return unless status.local? && !status.reblog?

View File

@ -0,0 +1,25 @@
.features-list
.features-list__row
.text
%h6= t 'about.features.real_conversation_title'
= t 'about.features.real_conversation_body'
.visual
= fa_icon 'fw comments'
.features-list__row
.text
%h6= t 'about.features.not_a_product_title'
= t 'about.features.not_a_product_body'
.visual
= fa_icon 'fw users'
.features-list__row
.text
%h6= t 'about.features.within_reach_title'
= t 'about.features.within_reach_body'
.visual
= fa_icon 'fw mobile'
.features-list__row
.text
%h6= t 'about.features.humane_approach_title'
= t 'about.features.humane_approach_body'
.visual
= fa_icon 'fw leaf'

View File

@ -0,0 +1,15 @@
- if @instance_presenter.open_registrations
= render 'registration'
- else
= link_to t('auth.register_elsewhere'), 'https://joinmastodon.org', class: 'button button-primary'
.closed-registrations-message
- if @instance_presenter.closed_registrations_message.blank?
%p= t('about.closed_registrations')
- else
= @instance_presenter.closed_registrations_message.html_safe
.separator-or
%span= t('auth.or')
= link_to t('auth.login'), new_user_session_path, class: 'button button-alternative-2 webapp-btn'

View File

@ -0,0 +1,16 @@
.container-alt.links
.brand
= link_to root_url do
= image_tag asset_pack_path('logo_full.svg'), alt: 'Mastodon'
%ul.nav
%li
- if user_signed_in?
= link_to t('settings.back'), root_url, class: 'webapp-btn'
- else
= link_to t('auth.login'), new_user_session_path, class: 'webapp-btn'
%li= link_to t('about.about_this'), about_more_path
%li
= link_to 'https://joinmastodon.org/' do
= "#{t('about.other_instances')}"
%i.fa.fa-external-link{ style: 'padding-left: 5px;' }

View File

@ -1,28 +1,12 @@
= simple_form_for(new_user, url: user_registration_path) do |f|
.simple_form__overlay-area
%p.lead= t('about.federation_hint_html', instance: content_tag(:strong, site_hostname))
= f.simple_fields_for :account do |account_fields|
= account_fields.input :username, wrapper: :with_label, autofocus: true, label: false, required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.username'), :autocomplete => 'off', placeholder: t('simple_form.labels.defaults.username') }, append: "@#{site_hostname}", hint: false
.fields-group
= f.simple_fields_for :account do |account_fields|
= account_fields.input :username, wrapper: :with_label, label: false, required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.username'), :autocomplete => 'off', placeholder: t('simple_form.labels.defaults.username') }, append: "@#{site_hostname}", hint: false, disabled: closed_registrations?
= f.input :email, placeholder: t('simple_form.labels.defaults.email'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.email'), :autocomplete => 'off' }, hint: false
= f.input :password, placeholder: t('simple_form.labels.defaults.password'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.password'), :autocomplete => 'off' }, hint: false
= f.input :password_confirmation, placeholder: t('simple_form.labels.defaults.confirm_password'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.confirm_password'), :autocomplete => 'off' }, hint: false
= f.input :email, placeholder: t('simple_form.labels.defaults.email'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.email'), :autocomplete => 'off' }, hint: false, disabled: closed_registrations?
= f.input :password, placeholder: t('simple_form.labels.defaults.password'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.password'), :autocomplete => 'off' }, hint: false, disabled: closed_registrations?
= f.input :password_confirmation, placeholder: t('simple_form.labels.defaults.confirm_password'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.confirm_password'), :autocomplete => 'off' }, hint: false, disabled: closed_registrations?
.actions
= f.button :button, t('auth.register'), type: :submit, class: 'button button-primary'
- if approved_registrations?
.fields-group
= f.simple_fields_for :invite_request do |invite_request_fields|
= invite_request_fields.input :text, as: :text, wrapper: :with_block_label, required: false
.fields-group
= f.input :agreement, as: :boolean, wrapper: :with_label, label: t('auth.checkbox_agreement_html', rules_path: about_more_path, terms_path: terms_path), disabled: closed_registrations?
.actions
= f.button :button, sign_up_message, type: :submit, class: 'button button-primary', disabled: closed_registrations?
- if closed_registrations? && @instance_presenter.closed_registrations_message.present?
.simple_form__overlay-area__overlay
.simple_form__overlay-area__overlay__content.rich-formatting
.block-icon= fa_icon 'warning'
= @instance_presenter.closed_registrations_message.html_safe
%p.hint.subtle-hint=t('auth.agreement_html', rules_path: about_more_path, terms_path: terms_path)

View File

@ -3,78 +3,131 @@
- content_for :header_tags do
%link{ rel: 'canonical', href: about_url }/
%script#initial-state{ type: 'application/json' }!= json_escape(@initial_state_json)
= javascript_pack_tag 'about', integrity: true, crossorigin: 'anonymous'
= render partial: 'shared/og'
.landing
.landing__brand
= link_to root_url, class: 'brand' do
= image_pack_tag 'logo_full.svg', alt: 'Mastodon'
%span.brand__tagline=t 'about.tagline'
.landing-page.alternative
.header{ style: 'display: none' }
= image_pack_tag 'header-cybre-alt.jpg', alt: @instance_presenter.site_title
.container
.grid
.column-0
.brand
= link_to root_url do
= image_pack_tag 'logo-cybre.png'
= Setting.site_title
.landing__grid
.landing__grid__column.landing__grid__column-registration
.box-widget
= render 'registration'
- if Setting.timeline_preview
.column-1
.landing-page__forms
.brand
= link_to root_url do
= image_pack_tag 'logo_full.svg', alt: 'Mastodon'
.directory
- if Setting.profile_directory
.directory__tag
= optional_link_to Setting.profile_directory, explore_path do
%h4
= fa_icon 'address-book fw'
= t('about.discover_users')
%small= t('about.browse_directory')
= render 'forms'
.avatar-stack
- @instance_presenter.sample_accounts.each do |account|
= image_tag current_account&.user&.setting_auto_play_gif ? account.avatar_original_url : account.avatar_static_url, width: 48, height: 48, alt: '', class: 'account__avatar'
- else
.column-1.non-preview
.landing-page__forms
.brand
= link_to root_url do
= image_pack_tag 'logo_full.svg', alt: 'Mastodon'
- if Setting.timeline_preview
.directory__tag
= optional_link_to Setting.timeline_preview, public_timeline_path do
%h4
= fa_icon 'globe fw'
= t('about.see_whats_happening')
%small= t('about.browse_public_posts')
= render 'forms'
.directory__tag
= link_to 'https://joinmastodon.org/apps', target: '_blank', rel: 'noopener' do
%h4
= fa_icon 'tablet fw'
= t('about.get_apps')
%small= t('about.apps_platforms')
- if Setting.timeline_preview
.column-2
.landing-page__hero
= image_tag @instance_presenter.hero&.file&.url || @instance_presenter.thumbnail&.file&.url || asset_pack_path('background-cybre.png'), alt: @instance_presenter.site_title
.landing__grid__column.landing__grid__column-login
.box-widget
= render 'login'
.landing-page__information
.landing-page__short-description
.row
.landing-page__logo
= image_pack_tag 'logo-cybre.png', alt: 'Cybrespace'
.hero-widget
.hero-widget__img
= image_tag @instance_presenter.hero&.file&.url || @instance_presenter.thumbnail&.file&.url || asset_pack_path('media/images/preview.jpg'), alt: @instance_presenter.site_title
%h1
= @instance_presenter.site_title
%small!= t 'about.hosted_on', domain: content_tag(:span, site_hostname)
- if @instance_presenter.site_short_description.present?
.hero-widget__text
%p= @instance_presenter.site_description.html_safe.presence || t('about.generic_description', domain: site_hostname)
.landing-page__call-to-action{ dir: 'ltr' }
.row
.row__information-board
.information-board__section
%span= t 'about.user_count_before'
%strong= number_to_human @instance_presenter.user_count
%span= t 'about.user_count_after', count: @instance_presenter.user_count
.information-board__section
%strong= number_to_human @instance_presenter.active_user_count
%span= t 'about.active_count_after'
.row__mascot
.landing-page__mascot
.floats.float-1
= image_pack_tag 'floppy-3.svg'
.floats.float-2
= image_pack_tag 'floppy-1.svg'
.floats.float-3
= image_pack_tag 'floppy-2.svg'
- else
.column-2.non-preview
.landing-page__hero
= image_tag @instance_presenter.hero&.file&.url || @instance_presenter.thumbnail&.file&.url || asset_pack_path('preview.jpg'), alt: @instance_presenter.site_title
.landing-page__information
.landing-page__short-description
.row
.landing-page__logo
= image_pack_tag 'logo_transparent.svg', alt: 'Mastodon'
%h1
= @instance_presenter.site_title
%small!= t 'about.hosted_on', domain: content_tag(:span, site_hostname)
%p= @instance_presenter.site_description.html_safe.presence || t('about.generic_description', domain: site_hostname)
.landing-page__call-to-action
.row
.row__information-board
.information-board__section
%span= t 'about.user_count_before'
%strong= number_to_human @instance_presenter.user_count
%span= t 'about.user_count_after', count: @instance_presenter.user_count
.information-board__section
%strong= number_to_human @instance_presenter.active_user_count
%span= t 'about.active_count_after'
.row__mascot
.landing-page__mascot
= image_tag @instance_presenter.mascot&.file&.url || asset_pack_path('elephant_ui_plane.svg'), alt: ''
- if Setting.timeline_preview
.column-3
#mastodon-timeline{ data: { props: Oj.dump(default_props) } }
- if Setting.timeline_preview
.column-4.landing-page__information
.landing-page__features
.features-list
%div
%h3= t 'about.what_is_mastodon'
%p= t 'about.about_mastodon_html'
%div.contact
%h3= t 'about.administered_by'
= account_link_to(@instance_presenter.contact_account, link_to(t('about.learn_more'), about_more_path, class: 'button button-alternative'))
= render 'features'
.landing-page__features__action
= link_to t('about.learn_more'), 'https://joinmastodon.org/', class: 'button button-alternative'
.landing-page__footer
%p
= @instance_presenter.site_short_description.html_safe.presence
= link_to about_more_path do
= t('about.learn_more')
= fa_icon 'angle-double-right'
.hero-widget__footer
.hero-widget__footer__column
%h4= t 'about.administered_by'
= account_link_to @instance_presenter.contact_account
.hero-widget__footer__column
%h4= t 'about.server_stats'
%div{ style: 'display: flex' }
.hero-widget__counter{ style: 'width: 50%' }
%strong= number_to_human @instance_presenter.user_count, strip_insignificant_zeros: true
%span= t 'about.user_count_after', count: @instance_presenter.user_count
.hero-widget__counter{ style: 'width: 50%' }
%strong= number_to_human @instance_presenter.active_user_count, strip_insignificant_zeros: true
%span
= t 'about.active_count_after'
%abbr{ title: t('about.active_footnote') } *
#modal-container

View File

@ -23,6 +23,11 @@
= render 'header', account: @account, with_bio: true
- if @account.user&.disabled?
.header
.nav-center
%h2 This user's account has been locked by a moderator.
.grid
.column-0
.h-feed

View File

@ -6,7 +6,7 @@
.sidebar-wrapper
.sidebar
= link_to root_path do
= image_pack_tag 'logo.svg', class: 'logo', alt: 'Mastodon'
= image_pack_tag 'logo-cybre.png', class: 'logo', alt: 'Cybrespace'
= render_navigation
.content-wrapper

View File

@ -6,7 +6,7 @@
.logo-container
%h1
= link_to root_path do
= image_pack_tag 'logo_full.svg', alt: 'Mastodon'
= image_pack_tag 'logo-cybre.png', alt: 'Cybrespace'
.form-container
= render 'flashes'

View File

@ -7,7 +7,7 @@
.fields-row
.fields-row__column.fields-group.fields-row__column-6
= f.input :display_name, wrapper: :with_label, input_html: { maxlength: 30 }, hint: false
= f.input :note, wrapper: :with_label, input_html: { maxlength: 160 }, hint: false
= f.input :note, wrapper: :with_label, input_html: { maxlength: 413 }, hint: false
.fields-row
.fields-row__column.fields-row__column-6

View File

@ -69,7 +69,7 @@
= " "
·
= link_to remote_interaction_path(status, type: :favourite), class: 'modal-button detailed-status__link' do
= fa_icon('star')
= fa_icon('floppy-o')
%span.detailed-status__favorites>= number_to_human status.favourites_count, strip_insignificant_zeros: true
= " "

View File

@ -7,6 +7,8 @@
- unless media.file.meta.nil?
= opengraph 'og:image:width', media.file.meta.dig('original', 'width')
= opengraph 'og:image:height', media.file.meta.dig('original', 'height')
- if media.description.present?
= opengraph 'og:image:alt', media.description
- elsif media.video? || media.gifv?
- player_card = true
= opengraph 'og:image', full_asset_url(media.file.url(:small))

View File

@ -47,7 +47,6 @@
= fa_icon 'reply fw'
- else
= fa_icon 'reply-all fw'
.status__action-bar__counter__label= obscured_counter status.replies_count
= link_to remote_interaction_path(status, type: :reblog), class: 'status__action-bar-button icon-button modal-button', style: 'font-size: 18px; width: 23.1429px; height: 23.1429px; line-height: 23.15px;' do
- if status.public_visibility? || status.unlisted_visibility?
= fa_icon 'retweet fw'
@ -56,4 +55,4 @@
- else
= fa_icon 'envelope fw'
= link_to remote_interaction_path(status, type: :favourite), class: 'status__action-bar-button icon-button modal-button', style: 'font-size: 18px; width: 23.1429px; height: 23.1429px; line-height: 23.15px;' do
= fa_icon 'star fw'
= fa_icon 'floppy-o fw'

View File

@ -37,6 +37,7 @@ module Mastodon
# config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}').to_s]
config.i18n.available_locales = [
:en,
:'en-CY',
:ar,
:ast,
:bg,
@ -96,9 +97,11 @@ module Mastodon
]
config.i18n.default_locale = ENV['DEFAULT_LOCALE']&.to_sym
unless config.i18n.available_locales.include?(config.i18n.default_locale)
config.i18n.default_locale = :en
if config.i18n.available_locales.include?(config.i18n.default_locale)
config.i18n.fallbacks = [:en]
else
config.i18n.default_locale = :'en-CY'
config.i18n.fallbacks = [:en]
end
# config.paths.add File.join('app', 'api'), glob: File.join('**', '*.rb')

View File

@ -30,6 +30,7 @@ search:
- app/assets/images
- app/assets/fonts
- app/assets/videos
- app/javascript/images
ignore_missing:
- 'activemodel.errors.*'

View File

@ -0,0 +1,61 @@
---
en-CY:
devise:
confirmations:
confirmed: Your email address has been successfully confirmed.
send_instructions: You will receive an email with instructions for how to confirm your email address in a few minutes. Please check your spam folder if you didn't receive this email.
send_paranoid_instructions: If your email address exists in our database, you will receive an email with instructions for how to confirm your email address in a few minutes. Please check your spam folder if you didn't receive this email.
failure:
already_authenticated: You are already signed in.
inactive: Your account is not activated yet.
invalid: Invalid %{authentication_keys} or password.
last_attempt: You have one more attempt before your account is locked.
locked: Your account is locked.
not_found_in_database: Invalid %{authentication_keys} or password.
timeout: Your session expired. Please sign in again to continue.
unauthenticated: You need to sign in or sign up before continuing.
unconfirmed: You have to confirm your email address before continuing.
mailer:
confirmation_instructions:
subject: 'Mastodon: Confirmation instructions for %{instance}'
password_change:
subject: 'Mastodon: Password changed'
reset_password_instructions:
subject: 'Mastodon: Reset password instructions'
unlock_instructions:
subject: 'Mastodon: Unlock instructions'
omniauth_callbacks:
failure: Could not authenticate you from %{kind} because "%{reason}".
success: Successfully authenticated from %{kind} account.
passwords:
no_token: You can't access this page without coming from a password reset email. If you do come from a password reset email, please make sure you used the full URL provided.
send_instructions: If your email address exists in our database, you will receive a password recovery link at your email address in a few minutes. Please check your spam folder if you didn't receive this email.
send_paranoid_instructions: If your email address exists in our database, you will receive a password recovery link at your email address in a few minutes. Please check your spam folder if you didn't receive this email.
updated: Your password has been changed successfully. You are now signed in.
updated_not_active: Your password has been changed successfully.
registrations:
destroyed: Bye! Your account has been successfully cancelled. We hope to see you again soon.
signed_up: Welcome! You have signed up successfully.
signed_up_but_inactive: You have signed up successfully. However, we could not sign you in because your account is not yet activated.
signed_up_but_locked: You have signed up successfully. However, we could not sign you in because your account is locked.
signed_up_but_unconfirmed: A message with a confirmation link has been sent to your email address. Please follow the link to activate your account. Please check your spam folder if you didn't receive this email.
update_needs_confirmation: You updated your account successfully, but we need to verify your new email address. Please check your email and follow the confirm link to confirm your new email address. Please check your spam folder if you didn't receive this email.
updated: Your account has been updated successfully.
sessions:
already_signed_out: Signed out successfully.
signed_in: Signed in successfully.
signed_out: Signed out successfully.
unlocks:
send_instructions: You will receive an email with instructions for how to unlock your account in a few minutes. Please check your spam folder if you didn't receive this email.
send_paranoid_instructions: If your account exists, you will receive an email with instructions for how to unlock it in a few minutes. Please check your spam folder if you didn't receive this email.
unlocked: Your account has been unlocked successfully. Please sign in to continue.
errors:
messages:
already_confirmed: was already confirmed, please try signing in
confirmation_period_expired: needs to be confirmed within %{period}, please request a new one
expired: has expired, please request a new one
not_found: not found
not_locked: was not locked
not_saved:
one: '1 error prohibited this %{resource} from being saved:'
other: "%{count} errors prohibited this %{resource} from being saved:"

View File

@ -0,0 +1,119 @@
---
en-CY:
activerecord:
attributes:
doorkeeper/application:
name: Application name
redirect_uri: Redirect URI
scopes: Scopes
website: Application website
errors:
models:
doorkeeper/application:
attributes:
redirect_uri:
fragment_present: cannot contain a fragment.
invalid_uri: must be a valid URI.
relative_uri: must be an absolute URI.
secured_uri: must be an HTTPS/SSL URI.
doorkeeper:
applications:
buttons:
authorize: Authorize
cancel: Cancel
destroy: Destroy
edit: Edit
submit: Submit
confirmations:
destroy: Are you sure?
edit:
title: Edit application
form:
error: Whoops! Check your form for possible errors
help:
native_redirect_uri: Use %{native_redirect_uri} for local tests
redirect_uri: Use one line per URI
scopes: Separate scopes with spaces. Leave blank to use the default scopes.
index:
application: Application
callback_url: Callback URL
delete: Delete
name: Name
new: New application
scopes: Scopes
show: Show
title: Your applications
new:
title: New application
show:
actions: Actions
application_id: Client key
callback_urls: Callback URLs
scopes: Scopes
secret: Client secret
title: 'Application: %{name}'
authorizations:
buttons:
authorize: Authorize
deny: Deny
error:
title: An error has occurred
new:
able_to: It will be able to
prompt: Application %{client_name} requests access to your account
title: Authorization required
show:
title: Authorization code
authorized_applications:
buttons:
revoke: Revoke
confirmations:
revoke: Are you sure?
index:
application: Application
created_at: Authorized
date_format: "%Y-%m-%d %H:%M:%S"
scopes: Scopes
title: Your authorized applications
errors:
messages:
access_denied: The resource owner or authorization server denied the request.
credential_flow_not_configured: Resource Owner Password Credentials flow failed due to Doorkeeper.configure.resource_owner_from_credentials being unconfigured.
invalid_client: Client authentication failed due to unknown client, no client authentication included, or unsupported authentication method.
invalid_grant: The provided authorization grant is invalid, expired, revoked, does not match the redirection URI used in the authorization request, or was issued to another client.
invalid_redirect_uri: The redirect uri included is not valid.
invalid_request: The request is missing a required parameter, includes an unsupported parameter value, or is otherwise malformed.
invalid_resource_owner: The provided resource owner credentials are not valid, or resource owner cannot be found
invalid_scope: The requested scope is invalid, unknown, or malformed.
invalid_token:
expired: The access token expired
revoked: The access token was revoked
unknown: The access token is invalid
resource_owner_authenticator_not_configured: Resource Owner find failed due to Doorkeeper.configure.resource_owner_authenticator being unconfiged.
server_error: The authorization server encountered an unexpected condition which prevented it from fulfilling the request.
temporarily_unavailable: The authorization server is currently unable to handle the request due to a temporary overloading or maintenance of the server.
unauthorized_client: The client is not authorized to perform this request using this method.
unsupported_grant_type: The authorization grant type is not supported by the authorization server.
unsupported_response_type: The authorization server does not support this response type.
flash:
applications:
create:
notice: Application created.
destroy:
notice: Application deleted.
update:
notice: Application updated.
authorized_applications:
destroy:
notice: Application revoked.
layouts:
admin:
nav:
applications: Applications
oauth2_provider: OAuth2 Provider
application:
title: OAuth authorization required
scopes:
follow: follow, block, unblock and unfollow accounts
read: read your account's data
write: post on your behalf

563
config/locales/en-CY.yml Normal file
View File

@ -0,0 +1,563 @@
---
en-CY:
about:
about_hashtag_html: These are public pings tagged with <strong>#%{hashtag}</strong>. You can interact with them if you have an account anywhere in the fediverse
about_mastodon_html: Cybrespace is an instance of Mastodon, a social network based on open web protocols and free, open-source software. It is decentralized like e-mail.
about_this: About
closed_registrations: Registrations are currently closed on this instance. However! You can find a different instance to make an account on and get access to the very same network from there.
contact: Contact
contact_missing: Not set
contact_unavailable: N/A
description_headline: What is %{domain}?
domain_count_after: other instances
domain_count_before: Connected to
extended_description_html: |
<h3>A good place for rules</h3>
<p>The extended description has not been set up yet.</p>
features:
humane_approach_body: Learning from failures of other networks, Mastodon aims to make ethical design choices to combat the misuse of social media.
humane_approach_title: A more humane approach
not_a_product_body: Mastodon is not a commercial network. No advertising, no data mining, no walled gardens. There is no central authority.
not_a_product_title: Youre a person, not a product
real_conversation_body: With 512 characters at your disposal and support for granular content and media warnings, you can express yourself the way you want to.
real_conversation_title: Built for real conversation
within_reach_body: Multiple apps for iOS, Android, and other platforms thanks to a developer-friendly API ecosystem allow you to keep up with your friends anywhere.
within_reach_title: Always within reach
find_another_instance: Find another instance
generic_description: "%{domain} is one server in the network"
hosted_on: Mastodon hosted on %{domain}
learn_more: Learn more
other_instances: Instance list
source_code: Source code
status_count_after: pings
status_count_before: Who authored
user_count_after: users
user_count_before: Home to
what_is_mastodon: What is Mastodon?
accounts:
follow: Follow
followers: Followers
following: Following
media: Media
nothing_here: There is nothing here!
people_followed_by: People whom %{name} follows
people_who_follow: People who follow %{name}
posts: Pings
posts_with_replies: Pings with replies
remote_follow: Remote follow
reserved_username: The username is reserved
roles:
admin: Admin
unfollow: Unfollow
admin:
accounts:
are_you_sure: Are you sure?
confirm: Confirm
confirmed: Confirmed
disable_two_factor_authentication: Disable 2FA
display_name: Display name
domain: Domain
edit: Edit
email: E-mail
feed_url: Feed URL
followers: Followers
follows: Follows
inbox_url: Inbox URL
ip: IP
location:
all: All
local: Local
remote: Remote
title: Location
media_attachments: Media attachments
moderation:
all: All
silenced: Silenced
suspended: Suspended
title: Moderation
most_recent_activity: Most recent activity
most_recent_ip: Most recent IP
not_subscribed: Not subscribed
order:
alphabetic: Alphabetic
most_recent: Most recent
title: Order
outbox_url: Outbox URL
perform_full_suspension: Perform full suspension
profile_url: Profile URL
protocol: Protocol
public: Public
push_subscription_expires: PuSH subscription expires
redownload: Refresh avatar
reset: Reset
reset_password: Reset password
resubscribe: Resubscribe
salmon_url: Salmon URL
search: Query...
show:
created_reports: Reports created by this account
report: report
targeted_reports: Reports made about this account
silence: Silence
statuses: Statuses
subscribe: Subscribe
title: Accounts
undo_silenced: Undo silence
undo_suspension: Undo suspension
unsubscribe: Unsubscribe
username: Username
web: Web
domain_blocks:
add_new: Add new
created_msg: Domain block is now being processed
destroyed_msg: Domain block has been undone
domain: Domain
new:
create: Create block
hint: The domain block will not prevent creation of account entries in the database, but will retroactively and automatically apply specific moderation methods on those accounts.
severity:
desc_html: "<strong>Silence</strong> will make the account's posts invisible to anyone who isn't following them. <strong>Suspend</strong> will remove all of the account's content, media, and profile data. Use <strong>None</strong> if you just want to reject media files."
noop: None
silence: Silence
suspend: Suspend
title: New domain block
reject_media: Reject media files
reject_media_hint: Removes locally stored media files and refuses to download any in the future. Irrelevant for suspensions
severities:
noop: None
silence: Silence
suspend: Suspend
severity: Severity
show:
affected_accounts:
one: One account in the database affected
other: "%{count} accounts in the database affected"
retroactive:
silence: Unsilence all existing accounts from this domain
suspend: Unsuspend all existing accounts from this domain
title: Undo domain block for %{domain}
undo: Undo
title: Domain Blocks
undo: Undo
instances:
account_count: Known accounts
domain_name: Domain
title: Known Instances
reports:
action_taken_by: Action taken by
are_you_sure: Are you sure?
comment:
label: Comment
none: None
delete: Delete
id: ID
mark_as_resolved: Mark as resolved
nsfw:
'false': Unhide media attachments
'true': Hide media attachments
report: 'Report #%{id}'
report_contents: Contents
reported_account: Reported account
reported_by: Reported by
resolved: Resolved
silence_account: Silence account
status: Status
suspend_account: Suspend account
target: Target
title: Reports
unresolved: Unresolved
view: View
settings:
bootstrap_timeline_accounts:
desc_html: Separate multiple usernames by comma. Only local and unlocked accounts will work. Default when empty is all local admins.
title: Default follows for new users
contact_information:
email: Business e-mail
username: Contact username
registrations:
closed_message:
desc_html: Displayed on frontpage when registrations are closed. You can use HTML tags
title: Closed registration message
deletion:
desc_html: Allow anyone to delete their account
title: Open account deletion
open:
desc_html: Allow anyone to create an account
title: Open registration
site_description:
desc_html: Introductory paragraph on the frontpage and in meta tags. You can use HTML tags, in particular <code>&lt;a&gt;</code> and <code>&lt;em&gt;</code>.
title: Instance description
site_description_extended:
desc_html: A good place for your code of conduct, rules, guidelines and other things that set your instance apart. You can use HTML tags
title: Custom extended information
site_terms:
desc_html: You can write your own privacy policy, terms of service or other legalese. You can use HTML tags
title: Custom terms of service
site_title: Instance name
timeline_preview:
desc_html: Display public timeline on landing page
title: Timeline preview
title: Site Settings
statuses:
back_to_account: Back to account page
batch:
delete: Delete
nsfw_off: NSFW OFF
nsfw_on: NSFW ON
execute: Execute
failed_to_execute: Failed to execute
media:
hide: Hide media
show: Show media
title: Media
no_media: No media
title: Account statuses
with_media: With media
subscriptions:
callback_url: Callback URL
confirmed: Confirmed
expires_in: Expires in
last_delivery: Last delivery
title: WebSub
topic: Topic
title: Administration
admin_mailer:
new_report:
body: "%{reporter} has reported %{target}"
subject: New report for %{instance} (#%{id})
application_mailer:
salutation: "%{name},"
settings: 'Change e-mail preferences: %{link}'
signature: Mastodon notifications from %{instance}
view: 'View:'
applications:
created: Application successfully created
destroyed: Application successfully deleted
invalid_url: The provided URL is invalid
regenerate_token: Regenerate access token
token_regenerated: Access token successfully regenerated
warning: Be very careful with this data. Never share it with anyone!
your_token: Your access token
auth:
agreement_html: By signing up you agree to <a href="%{rules_path}">our terms of service</a> and <a href="%{terms_path}">privacy policy</a>.
change_password: Security
delete_account: Delete account
delete_account_html: If you wish to delete your account, you can <a href="%{path}">proceed here</a>. You will be asked for confirmation.
didnt_get_confirmation: Didn't receive confirmation instructions?
forgot_password: Forgot your password?
invalid_reset_password_token: Password reset token is invalid or expired. Please try again.
login: Jack in
logout: Jack out
register: Apply for upload
resend_confirmation: Resend confirmation instructions
reset_password: Reset password
set_new_password: Set new password
authorize_follow:
error: Unfortunately, there was an error looking up the remote account
follow: Follow
follow_request: 'You have sent a follow request to:'
following: 'Success! You are now following:'
post_follow:
close: Or, you can just close this window.
return: Return to the user's profile
web: Go to web
title: Follow %{acct}
datetime:
distance_in_words:
about_x_hours: "%{count}h"
about_x_months: "%{count}mo"
about_x_years: "%{count}y"
almost_x_years: "%{count}y"
half_a_minute: Just now
less_than_x_minutes: "%{count}m"
less_than_x_seconds: Just now
over_x_years: "%{count}y"
x_days: "%{count}d"
x_minutes: "%{count}m"
x_months: "%{count}mo"
x_seconds: "%{count}s"
deletes:
bad_password_msg: Nice try, hackers! Incorrect password
confirm_password: Enter your current password to verify your identity
description_html: This will <strong>permanently, irreversibly</strong> remove content from your account and deactivate it. Your username will remain reserved to prevent future impersonations.
proceed: Delete account
success_msg: Your account was successfully deleted
warning_html: Only deletion of content from this particular instance is guaranteed. Content that has been widely shared is likely to leave traces. Offline servers and servers that have unsubscribed from your updates will not update their databases.
warning_title: Disseminated content availability
errors:
'403': You don't have permission to view this page.
'404': The page you were looking for doesn't exist.
'410': The page you were looking for doesn't exist anymore.
'422':
content: Security verification failed. Are you blocking cookies?
title: Security verification failed
'429': Throttled
noscript_html: To use the Mastodon web application, please enable JavaScript. Alternatively, try one of the <a href="https://github.com/tootsuite/documentation/blob/master/Using-Mastodon/Apps.md">native apps</a> for Mastodon for your platform.
exports:
blocks: You block
csv: CSV
follows: You follow
mutes: You mute
storage: Media storage
followers:
domain: Domain
explanation_html: If you want to ensure the privacy of your pings , you must be aware of who is following you. <strong>Your private pings are delivered to all instances where you have followers</strong>. You may wish to review them, and remove followers if you do not trust your privacy to be respected by the staff or software of those instances.
followers_count: Number of followers
lock_link: Lock your account
purge: Remove from followers
success:
one: In the process of soft-blocking followers from one domain...
other: In the process of soft-blocking followers from %{count} domains...
true_privacy_html: Please mind that <strong>true privacy can only be achieved with end-to-end encryption</strong>.
unlocked_warning_html: Anyone can follow you to immediately view your private pings. %{lock_link} to be able to review and reject followers.
unlocked_warning_title: Your account is not locked
generic:
changes_saved_msg: Changes successfully saved!
powered_by: powered by %{link}
save_changes: Save changes
validation_errors:
one: Something isn't quite right yet! Please review the error below
other: Something isn't quite right yet! Please review %{count} errors below
imports:
preface: You can import data that you have exported from another instance, such as a list of the people you are following or blocking.
success: Your data was successfully uploaded and will now be processed in due time
types:
blocking: Blocking list
following: Following list
muting: Muting list
upload: Upload
landing_strip_html: "<strong>%{name}</strong> is a user on %{link_to_root_path}. You can follow them or interact with them if you have an account anywhere in the fediverse."
landing_strip_signup_html: If you don't, you can <a href="%{sign_up_path}">sign up here</a>.
media_attachments:
validations:
images_and_video: Cannot attach a video to a ping that already contains images
too_many: Cannot attach more than 4 files
notification_mailer:
digest:
body: 'Here is a brief summary of what you missed on %{instance} since your last visit on %{since}:'
mention: "%{name} mentioned you in:"
new_followers_summary:
one: You have acquired one new follower! Yay!
other: You have gotten %{count} new followers! Amazing!
subject:
one: "1 new notification since your last visit \U0001F418"
other: "%{count} new notifications since your last visit \U0001F418"
favourite:
body: 'Your ping was florped by %{name}:'
subject: "%{name} florped your ping"
follow:
body: "%{name} is now following you!"
subject: "%{name} is now following you"
follow_request:
body: "%{name} has requested to follow you"
subject: 'Pending follower: %{name}'
mention:
body: 'You were mentioned by %{name} in:'
subject: You were mentioned by %{name}
reblog:
body: 'Your ping was relayed by %{name}:'
subject: "%{name} relayed your ping"
number:
human:
decimal_units:
format: "%n%u"
units:
billion: B
million: M
quadrillion: Q
thousand: K
trillion: T
unit: ''
pagination:
next: Next
prev: Prev
truncate: "&hellip;"
push_notifications:
favourite:
title: "%{name} favourited your status"
follow:
title: "%{name} is now following you"
group:
title: "%{count} notifications"
mention:
action_boost: Boost
action_expand: Show more
action_favourite: Favourite
title: "%{name} mentioned you"
reblog:
title: "%{name} boosted your status"
remote_follow:
acct: Enter your username@domain you want to follow from
missing_resource: Could not find the required redirect URL for your account
proceed: Proceed to follow
prompt: 'You are going to follow:'
sessions:
activity: Last activity
browser: Browser
browsers:
alipay: Alipay
blackberry: Blackberry
chrome: Chrome
edge: Microsoft Edge
firefox: Firefox
generic: Unknown browser
ie: Internet Explorer
micro_messenger: MicroMessenger
nokia: Nokia S40 Ovi Browser
opera: Opera
phantom_js: PhantomJS
qq: QQ Browser
safari: Safari
uc_browser: UCBrowser
weibo: Weibo
current_session: Current session
description: "%{browser} on %{platform}"
explanation: These are the web browsers currently logged in to your cybre.space account.
ip: IP
platforms:
adobe_air: Adobe Air
android: Android
blackberry: Blackberry
chrome_os: ChromeOS
firefox_os: Firefox OS
ios: iOS
linux: Linux
mac: Mac
other: unknown platform
windows: Windows
windows_mobile: Windows Mobile
windows_phone: Windows Phone
revoke: Revoke
revoke_success: Session successfully revoked
title: Sessions
settings:
authorized_apps: Authorized apps
back: Back to Mastodon
delete: Account deletion
development: Development
edit_profile: edit ~/.profile
export: Data export
followers: Authorized followers
import: Import
preferences: Preferences
settings: Settings
two_factor_authentication: Two-factor Authentication
your_apps: Your applications
statuses:
open_in_web: Open in web
over_character_limit: character limit of %{max} exceeded
pin_errors:
limit: You have already pinned the maximum number of pings
ownership: Someone else's ping cannot be pinned
private: Non-public pings cannot be pinned
reblog: A boost cannot be pinned
show_more: Show more
visibilities:
private: Followers-only
private_long: Only show to followers
public: Public
public_long: Everyone can see
unlisted: Unlisted
unlisted_long: Everyone can see, but not listed on public timelines
stream_entries:
click_to_show: Click to show
pinned: Pinned ping
reblogged: relayed
sensitive_content: Sensitive content
terms:
body_html: |
<h2>Privacy Policy</h2>
<h3 id="collect">What information do we collect?</h3>
<p>We collect information from you when you register on our site and gather data when you participate in the forum by reading, writing, and evaluating the content shared here.</p>
<p>When registering on our site, you may be asked to enter your name and e-mail address. You may, however, visit our site without registering. Your e-mail address will be verified by an email containing a unique link. If that link is visited, we know that you control the e-mail address.</p>
<p>When registered and posting, we record the IP address that the post originated from. We also may retain server logs which include the IP address of every request to our server.</p>
<h3 id="use">What do we use your information for?</h3>
<p>Any of the information we collect from you may be used in one of the following ways:</p>
<ul>
<li>To personalize your experience &mdash; your information helps us to better respond to your individual needs.</li>
<li>To improve our site &mdash; we continually strive to improve our site offerings based on the information and feedback we receive from you.</li>
<li>To improve customer service &mdash; your information helps us to more effectively respond to your customer service requests and support needs.</li>
<li>To send periodic emails &mdash; The email address you provide may be used to send you information, notifications that you request about changes to topics or in response to your user name, respond to inquiries, and/or other requests or questions.</li>
</ul>
<h3 id="protect">How do we protect your information?</h3>
<p>We implement a variety of security measures to maintain the safety of your personal information when you enter, submit, or access your personal information.</p>
<h3 id="data-retention">What is your data retention policy?</h3>
<p>We will make a good faith effort to:</p>
<ul>
<li>Retain server logs containing the IP address of all requests to this server no more than 90 days.</li>
<li>Retain the IP addresses associated with registered users and their posts no more than 5 years.</li>
</ul>
<h3 id="cookies">Do we use cookies?</h3>
<p>Yes. Cookies are small files that a site or its service provider transfers to your computer's hard drive through your Web browser (if you allow). These cookies enable the site to recognize your browser and, if you have a registered account, associate it with your registered account.</p>
<p>We use cookies to understand and save your preferences for future visits and compile aggregate data about site traffic and site interaction so that we can offer better site experiences and tools in the future. We may contract with third-party service providers to assist us in better understanding our site visitors. These service providers are not permitted to use the information collected on our behalf except to help us conduct and improve our business.</p>
<h3 id="disclose">Do we disclose any information to outside parties?</h3>
<p>We do not sell, trade, or otherwise transfer to outside parties your personally identifiable information. This does not include trusted third parties who assist us in operating our site, conducting our business, or servicing you, so long as those parties agree to keep this information confidential. We may also release your information when we believe release is appropriate to comply with the law, enforce our site policies, or protect ours or others rights, property, or safety. However, non-personally identifiable visitor information may be provided to other parties for marketing, advertising, or other uses.</p>
<h3 id="third-party">Third party links</h3>
<p>Occasionally, at our discretion, we may include or offer third party products or services on our site. These third party sites have separate and independent privacy policies. We therefore have no responsibility or liability for the content and activities of these linked sites. Nonetheless, we seek to protect the integrity of our site and welcome any feedback about these sites.</p>
<h3 id="coppa">Children's Online Privacy Protection Act Compliance</h3>
<p>Our site, products and services are all directed to people who are at least 13 years old. If this server is in the USA, and you are under the age of 13, per the requirements of COPPA (<a href="https://en.wikipedia.org/wiki/Children%27s_Online_Privacy_Protection_Act">Children's Online Privacy Protection Act</a>) do not use this site.</p>
<h3 id="online">Online Privacy Policy Only</h3>
<p>This online privacy policy applies only to information collected through our site and not to information collected offline.</p>
<h3 id="consent">Your Consent</h3>
<p>By using our site, you consent to our web site privacy policy.</p>
<h3 id="changes">Changes to our Privacy Policy</h3>
<p>If we decide to change our privacy policy, we will post those changes on this page.</p>
<p>This document is CC-BY-SA. It was last updated May 31, 2013.</p>
<p>Originally adapted from the <a href="https://github.com/discourse/discourse">Discourse privacy policy</a>.</p>
title: "%{instance} Terms of Service and Privacy Policy"
themes:
default: Cybrespace
mastodon: Mastodon
win95: 95
time:
formats:
default: "%b %d, %Y, %H:%M"
two_factor_authentication:
code_hint: Enter the code generated by your authenticator app to confirm
description_html: If you enable <strong>two-factor authentication</strong>, logging in will require you to be in possession of your phone, which will generate tokens for you to enter.
disable: Disable
enable: Enable
enabled: Two-factor authentication is enabled
enabled_success: Two-factor authentication successfully enabled
generate_recovery_codes: Generate recovery codes
instructions_html: "<strong>Scan this QR code into Google Authenticator or a similiar TOTP app on your phone</strong>. From now on, that app will generate tokens that you will have to enter when logging in."
lost_recovery_codes: Recovery codes allow you to regain access to your account if you lose your phone. If you've lost your recovery codes, you can regenerate them here. Your old recovery codes will be invalidated.
manual_instructions: 'If you can''t scan the QR code and need to enter it manually, here is the plain-text secret:'
recovery_codes: Backup recovery codes
recovery_codes_regenerated: Recovery codes successfully regenerated
recovery_instructions_html: If you ever lose access to your phone, you can use one of the recovery codes below to regain access to your account. <strong>Keep the recovery codes safe</strong>. For example, you may print them and store them with other important documents.
setup: Set up
wrong_code: The entered code was invalid! Are server time and device time correct?
users:
invalid_email: The e-mail address is invalid
invalid_otp_token: Invalid two-factor code
signed_in_as: 'Signed in as:'

View File

@ -1006,8 +1006,11 @@ en:
title: "%{instance} Terms of Service and Privacy Policy"
themes:
contrast: Mastodon (High contrast)
default: Mastodon (Dark)
mastodon-light: Mastodon (Light)
default: Cybrespace
mastodon: Mastodon (Dark)
mastodon-light: Mastodon (light)
light: Cybre Lite
win95: Windows 95
time:
formats:
default: "%b %d, %Y, %H:%M"

View File

@ -0,0 +1,127 @@
---
en-CY:
simple_form:
hints:
account_warning_preset:
text: You can use ping syntax, such as URLs, hashtags and mentions
admin_account_action:
send_email_notification: The user will receive an explanation of what happened with their account
text_html: Optional. You can use ping syntax. You can <a href="%{path}">add warning presets</a> to save time
type_html: Choose what to do with <strong>%{acct}</strong>
warning_preset_id: Optional. You can still add custom text to end of the preset
defaults:
autofollow: People who sign up through the invite will automatically follow you
avatar: PNG, GIF or JPG. At most %{size}. Will be downscaled to %{dimensions}px
bot: This account mainly performs automated actions and might not be monitored
context: One or multiple contexts where the filter should apply
digest: Only sent after a long period of inactivity and only if you have received any personal messages in your absence
discoverable_html: The <a href="%{path}" target="_blank">directory</a> lets people find accounts based on interests and activity. Requires at least %{min_followers} followers
email: You will be sent a confirmation e-mail
fields: You can have up to 4 items displayed as a table on your profile
header: PNG, GIF or JPG. At most %{size}. Will be downscaled to %{dimensions}px
inbox_url: Copy the URL from the frontpage of the relay you want to use
irreversible: Filtered pings will disappear irreversibly, even if filter is later removed
locale: The language of the user interface, e-mails and push notifications
locked: Requires you to manually approve followers
password: Use at least 8 characters
phrase: Will be matched regardless of casing in text or content warning of a pings
scopes: Which APIs the application will be allowed to access. If you select a top-level scope, you don't need to select individual ones.
setting_aggregate_reblogs: Do not show new relays for pings that have been recently relayed (only affects newly-received relays)
setting_default_language: The language of your pings can be detected automatically, but it's not always accurate
setting_display_media_default: Hide media marked as sensitive
setting_display_media_hide_all: Always hide all media
setting_display_media_show_all: Always show media marked as sensitive
setting_hide_network: Who you follow and who follows you will not be shown on your profile
setting_noindex: Affects your public profile and status pages
setting_theme: Affects how Mastodon looks when you're logged in from any device.
username: Your username will be unique on %{domain}
whole_word: When the keyword or phrase is alphanumeric only, it will only be applied if it matches the whole word
imports:
data: CSV file exported from another Mastodon instance
sessions:
otp: 'Enter the two-factor code generated by your phone app or use one of your recovery codes:'
user:
chosen_languages: When checked, only pings in selected languages will be displayed in public timelines
labels:
account:
fields:
name: Label
value: Content
account_warning_preset:
text: Preset text
admin_account_action:
send_email_notification: Notify the user per e-mail
text: Custom warning
type: Action
types:
disable: Disable
none: Do nothing
silence: Silence
suspend: Suspend and irreversibly delete account data
warning_preset_id: Use a warning preset
defaults:
autofollow: Invite to follow your account
avatar: Avatar
bot: This is a bot account
chosen_languages: Filter languages
confirm_new_password: Confirm new password
confirm_password: Confirm password
context: Filter contexts
current_password: Current password
data: Data
discoverable: List this account on the directory
display_name: Display name
email: E-mail address
expires_in: Expire after
fields: Profile metadata
header: Header
inbox_url: URL of the relay inbox
irreversible: Drop instead of hide
locale: Interface language
locked: Lock account
max_uses: Max number of uses
new_password: New password
note: Bio
otp_attempt: Two-factor code
password: Password
phrase: Keyword or phrase
setting_aggregate_reblogs: Group relays in timelines
setting_auto_play_gif: Auto-play animated GIFs
setting_boost_modal: Show confirmation dialog before relaying
setting_default_language: Posting language
setting_default_privacy: Post privacy
setting_default_sensitive: Always mark media as sensitive
setting_delete_modal: Show confirmation dialog before deleting a ping
setting_display_media: Media display
setting_display_media_default: Default
setting_display_media_hide_all: Hide all
setting_display_media_show_all: Show all
setting_expand_spoilers: Always expand pings marked with content warnings
setting_hide_network: Hide your network
setting_noindex: Opt-out of search engine indexing
setting_reduce_motion: Reduce motion in animations
setting_system_font_ui: Use system's default font
setting_theme: Site theme
setting_unfollow_modal: Show confirmation dialog before unfollowing someone
severity: Severity
type: Import type
username: Username
username_or_email: Username or Email
whole_word: Whole word
interactions:
must_be_follower: Block notifications from non-followers
must_be_following: Block notifications from people you don't follow
must_be_following_dm: Block direct messages from people you don't follow
notification_emails:
digest: Send digest e-mails
favourite: Send e-mail when someone favourites your status
follow: Send e-mail when someone follows you
follow_request: Send e-mail when someone requests to follow you
mention: Send e-mail when someone mentions you
reblog: Send e-mail when someone relays your status
report: Send e-mail when a new report is submitted
'no': 'No'
required:
mark: "*"
text: required
'yes': 'Yes'

View File

@ -2,7 +2,7 @@
# important settings can be changed from the admin interface.
defaults: &defaults
site_title: Mastodon
site_title: 'Cybrespace'
site_short_description: ''
site_description: ''
site_extended_description: ''

View File

@ -1,3 +1,6 @@
default: styles/application.scss
default: styles/cybre.scss
mastodon: styles/application.scss
contrast: styles/contrast.scss
mastodon-light: styles/mastodon-light.scss
light: styles/cybre-light.scss
win95: styles/win95.scss

View File

@ -31,6 +31,7 @@ default: &default
- .ttf
- .woff
- .woff2
- .gif
extensions:
- .mjs

Some files were not shown because too many files have changed in this diff Show More