the browser-facing portion of osu!
0
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge branch 'master' into comment-after

authored by

bakaneko and committed by
GitHub
23063bf7 7d9bd08e

+6789 -1361
+9 -3
.env.example
··· 69 69 # S3_BASE_URL= 70 70 # S3_MINI_URL= 71 71 72 + # S3_SOLO_REPLAY_BUCKET=solo-scores-replays 73 + 72 74 # S3_AVATAR_KEY= 73 75 # S3_AVATAR_SECRET= 74 76 # S3_AVATAR_REGION= ··· 136 138 STORE_NOTIFICATIONS_QUEUE=store-notifications 137 139 STORE_STALE_DAYS= 138 140 139 - PAYPAL_URL=https://www.sandbox.paypal.com/cgi-bin/webscr 140 - PAYPAL_MERCHANT_ID= 141 141 PAYPAL_CLIENT_ID= 142 142 PAYPAL_CLIENT_SECRET= 143 + PAYPAL_MERCHANT_ID= 143 144 PAYPAL_NO_SHIPPING_EXPERIENCE_PROFILE_ID= 145 + PAYPAL_URL=https://www.sandbox.paypal.com/cgi-bin/webscr 144 146 145 147 XSOLLA_API_KEY= 146 148 XSOLLA_MERCHANT_ID= ··· 148 150 XSOLLA_SECRET_KEY= 149 151 150 152 CENTILI_API_KEY= 153 + CENTILI_CONVERSION_RATE= 154 + CENTILI_ENABLED=false 151 155 CENTILI_SECRET_KEY= 152 - CENTILI_CONVERSION_RATE= 153 156 CENTILI_WIDGET_URL=https://api.centili.com/payment/widget 154 157 155 158 OSU_RUNNING_COST= ··· 317 320 # OSU_URL_LAZER_WINDOWS_X64='https://github.com/ppy/osu/releases/latest/download/install.exe' 318 321 # OSU_URL_LAZER_INFO= 319 322 # OSU_URL_USER_RESTRICTION=/wiki/Help_centre/Account_restrictions 323 + 324 + # USER_COUNTRY_CHANGE_MAX_MIXED_MONTHS=2 325 + # USER_COUNTRY_CHANGE_MIN_MONTHS=6
+1 -1
.eslintrc.js
··· 229 229 'new-parens': 'error', 230 230 'no-bitwise': 'error', 231 231 'no-caller': 'error', 232 - 'no-console': 'warn', 232 + 'no-console': ['error', { allow: ['error', 'warn'] }], 233 233 'no-empty-function': 'error', 234 234 'no-eval': 'error', 235 235 'no-invalid-this': 'error',
+1 -1
.github/workflows/lint.yml
··· 49 49 - name: Install js dependencies 50 50 run: yarn --frozen-lockfile 51 51 52 - - run: 'yarn lint --max-warnings 123 > /dev/null' 52 + - run: 'yarn lint --max-warnings 102 > /dev/null' 53 53 54 54 - run: ./bin/update_licence.sh -nf 55 55
+1 -1
.github/workflows/pack.yml
··· 71 71 run: | 72 72 export TITLE="Pending osu-web $PRODUCTION_TRACK Deployment: $GITHUB_REF_NAME" 73 73 export URL="https://github.com/ppy/osu-web/actions/runs/$GITHUB_RUN_ID" 74 - export DESCRIPTION="Docker image was built for tag $GITHUB_REF_NAME and awaiting approval for production deployment: 74 + export DESCRIPTION="Docker image was built for tag $GITHUB_REF_NAME and awaiting approval for $PRODUCTION_TRACK deployment: 75 75 [View Workflow Run]($URL)" 76 76 export ACTOR_ICON="https://avatars.githubusercontent.com/u/$GITHUB_ACTOR_ID" 77 77
+1 -1
.github/workflows/tests.yml
··· 13 13 DB_HOST: 127.0.0.1 14 14 ES_SOLO_SCORES_HOST: http://localhost:9200 15 15 GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} 16 - NOTIFICATION_ENDPOINT: ws://127.0.0.1:2345 16 + NOTIFICATION_ENDPOINT: ws://localhost:2345 17 17 OSU_INSTALL_DEV: 1 18 18 OSU_USE_SYSTEM_COMPOSER: 1 19 19 OSU_DB_CREATE: 1
+1 -2
app/Console/Commands/UserNotificationsCleanup.php
··· 6 6 namespace App\Console\Commands; 7 7 8 8 use App\Libraries\Notification\BatchIdentities; 9 - use App\Models\User; 10 9 use App\Models\UserNotification; 11 10 use Datadog; 12 11 use Illuminate\Console\Command; ··· 55 54 56 55 foreach ($notificationIdByUserIds as $userId => $notificationIds) { 57 56 UserNotification::batchDestroy( 58 - User::find($userId), 57 + $userId, 59 58 BatchIdentities::fromParams(['notifications' => $notificationIds]) 60 59 ); 61 60 $deleted = count($notificationIds);
+19 -3
app/Http/Controllers/AccountController.php
··· 7 7 8 8 use App\Exceptions\ImageProcessorException; 9 9 use App\Exceptions\ModelNotSavedException; 10 + use App\Libraries\User\CountryChange; 11 + use App\Libraries\User\CountryChangeTarget; 10 12 use App\Libraries\UserVerification; 11 13 use App\Libraries\UserVerificationState; 12 14 use App\Mail\UserEmailUpdated; ··· 40 42 'except' => [ 41 43 'edit', 42 44 'reissueCode', 45 + 'updateCountry', 43 46 'updateEmail', 44 47 'updateNotificationOptions', 45 48 'updateOptions', ··· 156 159 return json_item($user, new CurrentUserTransformer()); 157 160 } 158 161 162 + public function updateCountry() 163 + { 164 + $newCountry = get_string(Request::input('country_acronym')); 165 + $user = Auth::user(); 166 + 167 + if (CountryChangeTarget::get($user) !== $newCountry) { 168 + abort(403, 'specified country_acronym is not allowed'); 169 + } 170 + 171 + CountryChange::handle($user, $newCountry, 'account settings'); 172 + \Session::flash('popup', osu_trans('common.saved')); 173 + 174 + return ext_view('layout.ujs-reload', [], 'js'); 175 + } 176 + 159 177 public function updateEmail() 160 178 { 161 179 $params = get_params(request()->all(), 'user', ['current_password', 'user_email', 'user_email_confirmation']); ··· 267 285 Mail::to($user)->send(new UserPasswordUpdated($user)); 268 286 } 269 287 270 - $user->resetSessions(); 271 - $this->login($user); 272 - UserVerification::fromCurrentRequest()->markVerified(); 288 + $user->resetSessions(session()->getKey()); 273 289 274 290 return response([], 204); 275 291 } else {
+24 -8
app/Http/Controllers/Forum/TopicCoversController.php
··· 6 6 namespace App\Http\Controllers\Forum; 7 7 8 8 use App\Exceptions\ImageProcessorException; 9 + use App\Models\Forum\Forum; 9 10 use App\Models\Forum\Topic; 10 11 use App\Models\Forum\TopicCover; 11 12 use App\Transformers\Forum\TopicCoverTransformer; ··· 27 28 28 29 public function store() 29 30 { 30 - if (Request::hasFile('cover_file') !== true) { 31 + $params = get_params(Request::all(), null, [ 32 + 'cover_file:file', 33 + 'forum_id:int', 34 + 'topic_id:int', 35 + ], ['null_missing' => true]); 36 + 37 + if ($params['cover_file'] === null) { 31 38 abort(422); 32 39 } 33 40 34 - $topic = null; 35 - 36 - if (presence(Request::input('topic_id')) !== null) { 37 - $topic = Topic::with('forum')->findOrFail(Request::input('topic_id')); 41 + if ($params['topic_id'] === null) { 42 + if ($params['forum_id'] !== null) { 43 + $forum = Forum::findOrFail($params['forum_id']); 44 + } 45 + } else { 46 + $topic = Topic::with('forum')->findOrFail($params['topic_id']); 38 47 39 - priv_check('ForumTopicCoverStore', $topic->forum)->ensureCan(); 40 48 if ($topic->cover !== null) { 41 49 abort(422); 42 50 } 51 + 52 + $forum = $topic->forum; 43 53 } 44 54 55 + if (!isset($forum)) { 56 + abort(422, 'no forum specified'); 57 + } 58 + 59 + priv_check('ForumTopicCoverStore', $forum)->ensureCan(); 60 + 45 61 try { 46 62 $cover = TopicCover::upload( 47 - Request::file('cover_file')->getRealPath(), 63 + $params['cover_file'], 48 64 Auth::user(), 49 - $topic 65 + $topic ?? null, 50 66 ); 51 67 } catch (ImageProcessorException $e) { 52 68 return error_popup($e->getMessage());
+1 -1
app/Http/Controllers/NotificationsController.php
··· 26 26 public function batchDestroy() 27 27 { 28 28 UserNotification::batchDestroy( 29 - auth()->user(), 29 + auth()->id(), 30 30 BatchIdentities::fromParams(request()->all()) 31 31 ); 32 32
+10 -2
app/Http/Controllers/RankingController.php
··· 223 223 224 224 public function kudosu() 225 225 { 226 - $users = User::default()->orderBy('osu_kudostotal', 'desc')->limit(50)->with('country')->get(); 226 + static $maxResults = 1000; 227 227 228 - return ext_view('rankings.kudosu', ['users' => $users]); 228 + $maxPage = $maxResults / static::PAGE_SIZE; 229 + $page = min(get_int(request('page')) ?? 1, $maxPage); 230 + 231 + $scores = User::default() 232 + ->with('country') 233 + ->orderBy('osu_kudostotal', 'desc') 234 + ->paginate(static::PAGE_SIZE, ['*'], 'page', $page, $maxResults); 235 + 236 + return ext_view('rankings.kudosu', compact('scores')); 229 237 } 230 238 231 239 public function spotlight($mode)
+2
app/Http/Controllers/UsersController.php
··· 271 271 * |------------ | ----- 272 272 * | favourite | | 273 273 * | graveyard | | 274 + * | guest | | 274 275 * | loved | | 275 276 * | most_played | | 277 + * | nominated | | 276 278 * | pending | Previously `unranked` 277 279 * | ranked | Previously `ranked_and_approved` 278 280 *
+1 -1
app/Jobs/UpdateUserForumTopicFollows.php
··· 47 47 48 48 $watch->delete(); 49 49 UserNotification::batchDestroy( 50 - $user, 50 + $user->getKey(), 51 51 BatchIdentities::fromParams(['identities' => [ 52 52 [ 53 53 'object_id' => $topic->getKey(),
+6 -1
app/Libraries/NewForumTopic.php
··· 7 7 8 8 use App\Models\Forum\Forum; 9 9 use App\Models\Forum\Post; 10 + use App\Models\Forum\TopicCover; 10 11 use App\Models\User; 12 + use App\Transformers\Forum\TopicCoverTransformer; 11 13 use Carbon\Carbon; 12 14 13 15 class NewForumTopic ··· 18 20 19 21 public function cover() 20 22 { 21 - return json_item(null, 'Forum/TopicCover'); 23 + $cover = new TopicCover(); 24 + $cover->newForumId = $this->forum->getKey(); 25 + 26 + return json_item($cover, new TopicCoverTransformer()); 22 27 } 23 28 24 29 public function post()
+2 -4
app/Libraries/OrderCheckout.php
··· 224 224 */ 225 225 private function allowCentiliPayment() 226 226 { 227 - // Geolocation header from Cloudflare 228 - $isJapan = strcasecmp(request_country(), 'JP') === 0; 229 - 230 - return $isJapan 227 + return config('payments.centili.enabled') 228 + && strcasecmp(request_country(), 'JP') === 0 231 229 && !$this->order->requiresShipping() 232 230 && Request::input('intl') !== '1'; 233 231 }
+21 -2
app/Libraries/Search/BeatmapsetQueryParser.php
··· 59 59 $option = static::makeIntRangeOption($op, $m['value']); 60 60 break; 61 61 case 'status': 62 - $option = static::makeIntRangeOption($op, Beatmapset::STATES[$m['value']] ?? null); 62 + $option = static::makeIntRangeOption($op, static::statePrefixSearch($m['value'])); 63 63 break; 64 64 case 'creator': 65 65 $option = static::makeTextOption($op, $m['value']); ··· 108 108 $startTime = Carbon::create($m['year'], $m['month'], $m['day'], 0, 0, 0, 'UTC'); 109 109 $endTimeFunction = 'addDays'; 110 110 } else { 111 - $startTime = parse_time_to_carbon($value); 111 + $startTime = parse_time_to_carbon($value)?->utc(); 112 112 $endTimeFunction = 'addSeconds'; 113 113 } 114 114 ··· 223 223 if ($operator === '=') { 224 224 return presence(trim($value, '"')); 225 225 } 226 + } 227 + 228 + private static function statePrefixSearch($value): ?int 229 + { 230 + if (!present($value)) { 231 + return null; 232 + } 233 + 234 + if (isset(Beatmapset::STATES[$value])) { 235 + return Beatmapset::STATES[$value]; 236 + } 237 + 238 + foreach (Beatmapset::STATES as $string => $int) { 239 + if (starts_with($string, $value)) { 240 + return $int; 241 + } 242 + } 243 + 244 + return null; 226 245 } 227 246 }
+1 -1
app/Libraries/Search/ScoreSearch.php
··· 106 106 throw new Exception("Indexable and indexed score counts still don't match. Queue runner is probably either having problem, not running, or too slow"); 107 107 } 108 108 109 - public function queueForIndex(?array $schemas = null, array $ids): void 109 + public function queueForIndex(?array $schemas, array $ids): void 110 110 { 111 111 $count = count($ids); 112 112
+6 -1
app/Libraries/Session/Store.php
··· 15 15 { 16 16 const SESSION_ID_LENGTH = 40; 17 17 18 - public static function destroy($userId) 18 + public static function destroy($userId, ?string $excludedSessionId = null) 19 19 { 20 20 if (!static::isUsingRedis()) { 21 21 return; 22 22 } 23 23 24 24 $keys = static::keys($userId); 25 + if ($excludedSessionId !== null) { 26 + $keys = array_filter($keys, fn ($key) => $key !== $excludedSessionId); 27 + } 25 28 UserSessionEvent::newLogout($userId, $keys)->broadcast(); 26 29 Redis::del(array_merge([static::listKey($userId)], $keys)); 27 30 } ··· 143 146 144 147 $userId = Auth::user()->user_id; 145 148 149 + // prevent the following save from clearing up current flash data 150 + $this->reflash(); 146 151 // flush the current session data to redis early, otherwise we will get stale metadata for the current session 147 152 $this->save(); 148 153
+46
app/Libraries/User/CountryChange.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + declare(strict_types=1); 7 + 8 + namespace App\Libraries\User; 9 + 10 + use App\Exceptions\InvariantException; 11 + use App\Models\Beatmap; 12 + use App\Models\Country; 13 + use App\Models\User; 14 + use App\Models\UserAccountHistory; 15 + 16 + class CountryChange 17 + { 18 + public static function handle(User $user, string $newCountry, string $reason): void 19 + { 20 + // Assert valid country acronym 21 + $country = Country::find($newCountry); 22 + if ($country === null) { 23 + throw new InvariantException('invalid country specified'); 24 + } 25 + 26 + if ($user->country_acronym === $newCountry) { 27 + return; 28 + } 29 + 30 + $user->getConnection()->transaction(function () use ($newCountry, $reason, $user) { 31 + $oldCountry = $user->country_acronym; 32 + $user->update(['country_acronym' => $newCountry]); 33 + foreach (Beatmap::MODES as $ruleset => $_rulesetId) { 34 + $user->statistics($ruleset, true)->update(['country_acronym' => $newCountry]); 35 + $user->scoresBest($ruleset, true)->update(['country_acronym' => $newCountry]); 36 + } 37 + UserAccountHistory::addNote($user, "Changing country from {$oldCountry} to {$newCountry} ({$reason})"); 38 + }); 39 + 40 + \Artisan::queue('es:index-scores:queue', [ 41 + '--all' => true, 42 + '--no-interaction' => true, 43 + '--user' => $user->getKey(), 44 + ]); 45 + } 46 + }
+106
app/Libraries/User/CountryChangeTarget.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + declare(strict_types=1); 7 + 8 + namespace App\Libraries\User; 9 + 10 + use App\Models\Tournament; 11 + use App\Models\TournamentRegistration; 12 + use App\Models\User; 13 + use App\Models\UserCountryHistory; 14 + use Carbon\CarbonImmutable; 15 + 16 + class CountryChangeTarget 17 + { 18 + const MIN_DAYS_MONTH = 15; 19 + 20 + public static function currentMonth(): CarbonImmutable 21 + { 22 + $now = CarbonImmutable::now(); 23 + $subMonths = $now->day > static::MIN_DAYS_MONTH ? 0 : 1; 24 + 25 + return $now->startOfMonth()->subMonths($subMonths); 26 + } 27 + 28 + public static function get(User $user): ?string 29 + { 30 + $minMonths = static::minMonths(); 31 + $now = CarbonImmutable::now(); 32 + $until = static::currentMonth(); 33 + $since = $until->subMonths($minMonths - 1); 34 + 35 + if (static::isUserInTournament($user)) { 36 + return null; 37 + } 38 + 39 + $history = $user 40 + ->userCountryHistory() 41 + ->whereBetween('year_month', [ 42 + UserCountryHistory::formatDate($since), 43 + UserCountryHistory::formatDate($until), 44 + ])->whereHas('country') 45 + ->get(); 46 + 47 + // First group countries by year_month 48 + $byMonth = []; 49 + foreach ($history as $entry) { 50 + $byMonth[$entry->year_month] ??= []; 51 + $byMonth[$entry->year_month][] = $entry->country_acronym; 52 + } 53 + 54 + // For each year_month, summarise each countries 55 + $byCountry = []; 56 + foreach ($byMonth as $countries) { 57 + $mixed = count($countries) > 1; 58 + foreach ($countries as $country) { 59 + $byCountry[$country] ??= [ 60 + 'total' => 0, 61 + 'mixed' => 0, 62 + ]; 63 + $byCountry[$country]['total']++; 64 + if ($mixed) { 65 + $byCountry[$country]['mixed']++; 66 + } 67 + } 68 + } 69 + 70 + // Finally find the first country which fulfills the requirement 71 + foreach ($byCountry as $country => $data) { 72 + if ($data['total'] === $minMonths && $data['mixed'] <= static::maxMixedMonths()) { 73 + if ($user->country_acronym === $country) { 74 + return null; 75 + } else { 76 + return $country; 77 + } 78 + } 79 + } 80 + 81 + return null; 82 + } 83 + 84 + public static function maxMixedMonths(): int 85 + { 86 + return config('osu.user.country_change.max_mixed_months'); 87 + } 88 + 89 + public static function minMonths(): int 90 + { 91 + return config('osu.user.country_change.min_months'); 92 + } 93 + 94 + private static function isUserInTournament(User $user): bool 95 + { 96 + return TournamentRegistration 97 + ::where('user_id', $user->getKey()) 98 + ->whereIn( 99 + 'tournament_id', 100 + Tournament 101 + ::where('end_date', '>', CarbonImmutable::now()) 102 + ->orWhereNull('end_date') 103 + ->select('tournament_id'), 104 + )->exists(); 105 + } 106 + }
+1 -1
app/Libraries/UserRegistration.php
··· 63 63 64 64 $this->user->setDefaultGroup($this->group); 65 65 66 - Count::totalUsers()->increment('count'); 66 + Count::totalUsers()->incrementInstance('count'); 67 67 Datadog::increment('osu.new_account_registrations', 1, ['source' => 'osu-web']); 68 68 }); 69 69 } catch (Exception $e) {
+14 -4
app/Models/Comment.php
··· 182 182 public function setCommentable() 183 183 { 184 184 if ($this->parent_id === null || $this->parent === null) { 185 - return; 185 + if ($this->commentable_type !== null) { 186 + return; 187 + } 188 + // Reset the id if type is null otherwise Laravel will try to 189 + // "eager load" the commentable (whatever tha means in this context). 190 + // Note that setting type to random string doesn't work because 191 + // Laravel will happily try to create the random string class. 192 + // 193 + // Reference: https://github.com/laravel/framework/blob/53b02b3c1d926c095cccca06883a35a5c6729773/src/Illuminate/Database/Eloquent/Concerns/HasRelationships.php#L279-L281 194 + $this->commentable_id = null; 195 + } else { 196 + $this->commentable_id = $this->parent->commentable_id; 197 + $this->commentable_type = $this->parent->commentable_type; 186 198 } 187 199 188 - $this->commentable_id = $this->parent->commentable_id; 189 - $this->commentable_type = $this->parent->commentable_type; 190 200 $this->unsetRelation('commentable'); 191 201 } 192 202 ··· 244 254 return $this->getConnection()->transaction(function () use ($options) { 245 255 if (!$this->exists && $this->parent_id !== null && $this->parent !== null) { 246 256 // skips validation and everything 247 - $this->parent->increment('replies_count_cache'); 257 + $this->parent->incrementInstance('replies_count_cache'); 248 258 } 249 259 250 260 if ($this->isDirty('deleted_at')) {
+1 -1
app/Models/Forum/Topic.php
··· 532 532 throw $ex; 533 533 } 534 534 535 - $this->increment('topic_views'); 535 + $this->incrementInstance('topic_views'); 536 536 } elseif ($status->mark_time < $markTime) { 537 537 $status->update(['mark_time' => $markTime]); 538 538 }
+8
app/Models/Forum/TopicCover.php
··· 27 27 28 28 const MAX_DIMENSIONS = [2400, 580]; 29 29 30 + // To be passed to transformer for generating url for initial cover upload 31 + public ?int $newForumId = null; 32 + 30 33 protected $table = 'forum_topic_covers'; 31 34 32 35 private $_owner = [false, null]; ··· 114 117 } catch (Exception $_e) { 115 118 // do nothing 116 119 } 120 + } 121 + 122 + public function getForumId(): ?int 123 + { 124 + return $this->topic?->forum_id ?? $this->newForumId; 117 125 } 118 126 }
+24
app/Models/Model.php
··· 174 174 $query->whereNotNull($column)->where($column, '<>', ''); 175 175 } 176 176 177 + /** 178 + * Just like decrement but only works on saved instance instead of falling back to entire model 179 + */ 180 + public function decrementInstance() 181 + { 182 + if (!$this->exists) { 183 + return false; 184 + } 185 + 186 + return $this->decrement(...func_get_args()); 187 + } 188 + 177 189 public function delete() 178 190 { 179 191 return $this->runAfterCommitWrapper(function () { 180 192 return parent::delete(); 181 193 }); 194 + } 195 + 196 + /** 197 + * Just like increment but only works on saved instance instead of falling back to entire model 198 + */ 199 + public function incrementInstance() 200 + { 201 + if (!$this->exists) { 202 + return false; 203 + } 204 + 205 + return $this->increment(...func_get_args()); 182 206 } 183 207 184 208 public function save(array $options = [])
+1 -6
app/Models/Multiplayer/Room.php
··· 598 598 return $this->getConnection()->transaction(function () use ($user, $playlistItem) { 599 599 $agg = UserScoreAggregate::new($user, $this); 600 600 if ($agg->isNew) { 601 - // sanity; if the object isn't saved, laravel will increment the entire table. 602 - if (!$this->exists) { 603 - $this->save(); 604 - } 605 - 606 - $this->increment('participant_count'); 601 + $this->incrementInstance('participant_count'); 607 602 } 608 603 609 604 $agg->updateUserAttempts();
+10 -11
app/Models/Multiplayer/UserScoreAggregate.php
··· 53 53 ]); 54 54 } 55 55 56 - public static function lookupOrDefault(User $user, Room $room): self 56 + public static function lookupOrDefault(User $user, Room $room): static 57 57 { 58 - $obj = static::firstOrNew([ 58 + return static::firstOrNew([ 59 + 'room_id' => $room->getKey(), 59 60 'user_id' => $user->getKey(), 60 - 'room_id' => $room->getKey(), 61 + ], [ 62 + 'accuracy' => 0, 63 + 'attempts' => 0, 64 + 'completed' => 0, 65 + 'pp' => 0, 66 + 'total_score' => 0, 61 67 ]); 62 - 63 - foreach (['total_score', 'accuracy', 'pp', 'attempts', 'completed'] as $key) { 64 - // init if required 65 - $obj->$key = $obj->$key ?? 0; 66 - } 67 - 68 - return $obj; 69 68 } 70 69 71 70 public static function updatePlaylistItemUserHighScore(PlaylistItemUserHighScore $highScore, Score $score) ··· 175 174 176 175 public function updateUserAttempts() 177 176 { 178 - $this->increment('attempts'); 177 + $this->incrementInstance('attempts'); 179 178 } 180 179 181 180 public function user()
+2
app/Models/NewsPost.php
··· 33 33 // in minutes 34 34 const CACHE_DURATION = 86400; 35 35 const VERSION = 3; 36 + // should be higher than landing limit 36 37 const DASHBOARD_LIMIT = 8; 38 + // also for number of large posts in user dashboard 37 39 const LANDING_LIMIT = 4; 38 40 39 41 const SORTS = [
+2 -2
app/Models/Score/Best/Model.php
··· 351 351 $userStats = $this->user?->statistics($this->getMode()); 352 352 353 353 if ($userStats !== null) { 354 - $userStats->decrement($statsColumn); 354 + $userStats->decrementInstance($statsColumn); 355 355 356 356 $nextBest = static::where([ 357 357 'beatmap_id' => $this->beatmap_id, ··· 365 365 $nextBestStatsColumn = static::RANK_TO_STATS_COLUMN_MAPPING[$nextBest->rank] ?? null; 366 366 367 367 if ($nextBestStatsColumn !== null) { 368 - $userStats->increment($nextBestStatsColumn); 368 + $userStats->incrementInstance($nextBestStatsColumn); 369 369 } 370 370 } 371 371 }
+2 -2
app/Models/Store/Product.php
··· 230 230 return; 231 231 } 232 232 233 - $this->increment('stock', $quantity); 233 + $this->incrementInstance('stock', $quantity); 234 234 } 235 235 236 236 public function reserve($quantity) ··· 239 239 return; 240 240 } 241 241 242 - $this->decrement('stock', $quantity); 242 + $this->decrementInstance('stock', $quantity); 243 243 244 244 // operating under the assumtion that the caller will prevent concurrent updates. 245 245 if ($this->stock < 0) {
+13 -11
app/Models/User.php
··· 139 139 * @property int $user_avatar_width 140 140 * @property string $user_birthday 141 141 * @property string|null $user_colour 142 + * @property-read Collection<UserCountryHistory> $userCountryHistory 142 143 * @property string $user_dateformat 143 144 * @property string|null $user_discord 144 145 * @property int $user_dst ··· 271 272 private $validateEmailConfirmation = false; 272 273 273 274 private $isSessionVerified; 275 + 276 + public function userCountryHistory(): HasMany 277 + { 278 + return $this->hasMany(UserCountryHistory::class); 279 + } 274 280 275 281 public function getAuthPassword() 276 282 { ··· 920 926 'tokens', 921 927 'topicWatches', 922 928 'userAchievements', 929 + 'userCountryHistory', 923 930 'userGroups', 924 931 'userNotifications', 925 932 'userPage', ··· 948 955 return $isGroup; 949 956 } 950 957 951 - $groupModes = $this->findUserGroup($group, true)->playmodes; 958 + $groupModes = $this->findUserGroup($group, true)->actualRulesets(); 952 959 953 960 return in_array($playmode, $groupModes ?? [], true); 954 961 } ··· 1690 1697 $modes = []; 1691 1698 1692 1699 if ($this->isLimitedBN()) { 1693 - $playmodes = $this->findUserGroup(app('groups')->byIdentifier('bng_limited'), true)->playmodes ?? []; 1700 + $playmodes = $this->findUserGroup(app('groups')->byIdentifier('bng_limited'), true)->actualRulesets(); 1694 1701 foreach ($playmodes as $playmode) { 1695 1702 $modes[$playmode] = 'limited'; 1696 1703 } 1697 1704 } 1698 1705 1699 1706 if ($this->isFullBN()) { 1700 - $playmodes = $this->findUserGroup(app('groups')->byIdentifier('bng'), true)->playmodes ?? []; 1707 + $playmodes = $this->findUserGroup(app('groups')->byIdentifier('bng'), true)->actualRulesets(); 1701 1708 foreach ($playmodes as $playmode) { 1702 1709 $modes[$playmode] = 'full'; 1703 1710 } 1704 1711 } 1705 1712 1706 1713 if ($this->isNAT()) { 1707 - $playmodes = $this->findUserGroup(app('groups')->byIdentifier('nat'), true)->playmodes ?? []; 1714 + $playmodes = $this->findUserGroup(app('groups')->byIdentifier('nat'), true)->actualRulesets(); 1708 1715 foreach ($playmodes as $playmode) { 1709 1716 $modes[$playmode] = 'full'; 1710 1717 } ··· 1769 1776 return hash('sha256', $this->user_email).':'.hash('sha256', $this->user_password); 1770 1777 } 1771 1778 1772 - public function resetSessions(): void 1779 + public function resetSessions(?string $excludedSessionId = null): void 1773 1780 { 1774 - SessionStore::destroy($this->getKey()); 1781 + SessionStore::destroy($this->getKey(), $excludedSessionId); 1775 1782 $this 1776 1783 ->tokens() 1777 1784 ->with('refreshToken') ··· 1829 1836 } 1830 1837 1831 1838 return $this->fresh(); 1832 - } 1833 - 1834 - public function notificationCount() 1835 - { 1836 - return $this->user_unread_privmsg; 1837 1839 } 1838 1840 1839 1841 public function supportLength()
+52
app/Models/UserCountryHistory.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + declare(strict_types=1); 7 + 8 + namespace App\Models; 9 + 10 + use Illuminate\Database\Eloquent\Relations\BelongsTo; 11 + 12 + /** 13 + * @property int $count 14 + * @property Country $country 15 + * @property string $country_acronym 16 + * @property User $user 17 + * @property int $user_id 18 + * @property \Carbon\Carbon $last_updated 19 + * @property string $year_month 20 + */ 21 + class UserCountryHistory extends Model 22 + { 23 + public $incrementing = false; 24 + public $timestamps = false; 25 + 26 + protected $casts = ['last_updated' => 'datetime']; 27 + protected $primaryKey = ':composite'; 28 + protected $primaryKeys = ['user_id', 'year_month', 'country_acronym']; 29 + protected $table = 'user_country_history'; 30 + 31 + public static function formatDate(\DateTimeInterface $date): string 32 + { 33 + return $date->format('ym'); 34 + } 35 + 36 + public function country(): BelongsTo 37 + { 38 + return $this->belongsTo(Country::class, 'country_acronym'); 39 + } 40 + 41 + public function user(): BelongsTo 42 + { 43 + return $this->belongsTo(User::class, 'user_id'); 44 + } 45 + 46 + public function setYearMonthAttribute(\DateTimeInterface|string $value): void 47 + { 48 + $this->attributes['year_month'] = $value instanceof \DateTimeInterface 49 + ? static::formatDate($value) 50 + : $value; 51 + } 52 + }
+14
app/Models/UserGroup.php
··· 41 41 $this->attributes['playmodes'] = $this->group->has_playmodes ? json_encode($value ?? []) : null; 42 42 } 43 43 44 + public function actualRulesets(): array 45 + { 46 + static $defaultRulesets; 47 + $defaultRulesets ??= [ 48 + 'nat' => array_keys(Beatmap::MODES), 49 + ]; 50 + 51 + $visibleRulesets = $this->playmodes ?? []; 52 + 53 + return $visibleRulesets === [] 54 + ? ($defaultRulesets[$this->group->identifier] ?? []) 55 + : $visibleRulesets; 56 + } 57 + 44 58 public function getAttribute($key) 45 59 { 46 60 return match ($key) {
+6 -8
app/Models/UserNotification.php
··· 22 22 'is_read' => 'boolean', 23 23 ]; 24 24 25 - public static function batchDestroy(User $user, BatchIdentities $batchIdentities) 25 + public static function batchDestroy(int $userId, BatchIdentities $batchIdentities) 26 26 { 27 27 $notificationIds = $batchIdentities->getNotificationIds(); 28 28 $identities = $batchIdentities->getIdentities(); ··· 32 32 } 33 33 34 34 $now = now(); 35 + $userNotificationQuery = static::where(['user_id' => $userId]); 35 36 // obtain and filter valid user notification ids 36 - $ids = $user 37 - ->userNotifications() 37 + $ids = $userNotificationQuery->clone() 38 38 ->whereIn('notification_id', $notificationIds) 39 39 ->where('created_at', '<=', $now) 40 40 ->pluck('id') ··· 47 47 $readCount = 0; 48 48 49 49 foreach (array_chunk($ids, 1000) as $chunkedIds) { 50 - $unreadCountQuery = $user 51 - ->userNotifications() 50 + $unreadCountQuery = $userNotificationQuery->clone() 52 51 ->hasPushDelivery() 53 52 ->where('is_read', false) 54 53 ->whereIn('id', $chunkedIds); 55 54 $unreadCountInitial = $unreadCountQuery->count(); 56 - $user 57 - ->userNotifications() 55 + $userNotificationQuery->clone() 58 56 ->whereIn('id', $chunkedIds) 59 57 ->delete(); 60 58 ··· 62 60 $readCount += $unreadCountInitial - $unreadCountCurrent; 63 61 } 64 62 65 - (new NotificationDeleteEvent($user->getKey(), [ 63 + (new NotificationDeleteEvent($userId, [ 66 64 'notifications' => $identities, 67 65 'read_count' => $readCount, 68 66 'timestamp' => $now,
+5 -6
app/Transformers/Forum/TopicCoverTransformer.php
··· 10 10 11 11 class TopicCoverTransformer extends TransformerAbstract 12 12 { 13 - public function transform(TopicCover $cover = null) 13 + public function transform(TopicCover $cover) 14 14 { 15 - if ($cover === null) { 16 - $cover = new TopicCover(); 17 - } 18 - 19 15 if ($cover->getFileProperties() === null) { 20 16 $data = [ 21 17 'method' => 'post', 22 - 'url' => route('forum.topic-covers.store', ['topic_id' => $cover->topic_id]), 18 + 'url' => route('forum.topic-covers.store', [ 19 + 'forum_id' => $cover->getForumId(), 20 + 'topic_id' => $cover->topic_id, 21 + ]), 23 22 ]; 24 23 } else { 25 24 $data = [
+2 -1
app/Transformers/UserCompactTransformer.php
··· 405 405 406 406 public function includeUnreadPmCount(User $user) 407 407 { 408 - return $this->primitive($user->notificationCount()); 408 + // legacy pm has been turned off 409 + return $this->primitive(0); 409 410 } 410 411 411 412 public function includeUserAchievements(User $user)
+1 -1
bin/run_dusk.sh
··· 7 7 php artisan octane:start > /dev/null 2>&1 & 8 8 9 9 # run the tests 10 - php artisan dusk --verbose "$@" 10 + php artisan dusk "$@" 11 11 EXIT_CODE=$? 12 12 13 13 php artisan octane:stop
+7 -6
composer.lock
··· 11665 11665 }, 11666 11666 { 11667 11667 "name": "laravel/dusk", 11668 - "version": "v7.7.1", 11668 + "version": "v7.9.0", 11669 11669 "source": { 11670 11670 "type": "git", 11671 11671 "url": "https://github.com/laravel/dusk.git", 11672 - "reference": "836338ec355fc129b09f26f3cbc19de2daf065ad" 11672 + "reference": "a926506b105b93c473609bfe88b5da2347eeb7b2" 11673 11673 }, 11674 11674 "dist": { 11675 11675 "type": "zip", 11676 - "url": "https://api.github.com/repos/laravel/dusk/zipball/836338ec355fc129b09f26f3cbc19de2daf065ad", 11677 - "reference": "836338ec355fc129b09f26f3cbc19de2daf065ad", 11676 + "url": "https://api.github.com/repos/laravel/dusk/zipball/a926506b105b93c473609bfe88b5da2347eeb7b2", 11677 + "reference": "a926506b105b93c473609bfe88b5da2347eeb7b2", 11678 11678 "shasum": "" 11679 11679 }, 11680 11680 "require": { 11681 11681 "ext-json": "*", 11682 11682 "ext-zip": "*", 11683 + "guzzlehttp/guzzle": "^7.2", 11683 11684 "illuminate/console": "^9.0|^10.0", 11684 11685 "illuminate/support": "^9.0|^10.0", 11685 11686 "nesbot/carbon": "^2.0", ··· 11734 11735 ], 11735 11736 "support": { 11736 11737 "issues": "https://github.com/laravel/dusk/issues", 11737 - "source": "https://github.com/laravel/dusk/tree/v7.7.1" 11738 + "source": "https://github.com/laravel/dusk/tree/v7.9.0" 11738 11739 }, 11739 - "time": "2023-04-13T14:50:22+00:00" 11740 + "time": "2023-07-24T14:31:48+00:00" 11740 11741 }, 11741 11742 { 11742 11743 "name": "masterminds/html5",
+1 -1
config/filesystems.php
··· 102 102 'key' => env('S3_KEY'), 103 103 'secret' => env('S3_SECRET'), 104 104 'region' => env('S3_REGION'), 105 - 'bucket' => 'solo-scores-replay', 105 + 'bucket' => presence(env('S3_SOLO_REPLAY_BUCKET')) ?? 'solo-scores-replays', 106 106 ], 107 107 ], 108 108
+5
config/osu.php
··· 264 264 'registration_mode' => presence(env('REGISTRATION_MODE')) ?? 'client', 265 265 'super_friendly' => array_map('intval', explode(' ', env('SUPER_FRIENDLY', '3'))), 266 266 'ban_persist_days' => get_int(env('BAN_PERSIST_DAYS')) ?? 28, 267 + 268 + 'country_change' => [ 269 + 'max_mixed_months' => get_int(env('USER_COUNTRY_CHANGE_MAX_MIXED_MONTHS')) ?? 2, 270 + 'min_months' => get_int(env('USER_COUNTRY_CHANGE_MIN_MONTHS')) ?? 6, 271 + ], 267 272 ], 268 273 'user_report_notification' => [ 269 274 'endpoint_cheating' => presence(env('USER_REPORT_NOTIFICATION_ENDPOINT_CHEATING')),
+11 -6
config/payments.php
··· 1 1 <?php 2 2 3 3 return [ 4 + 'notification_channel' => env('STORE_NOTIFICATION_CHANNEL'), 5 + 'running_cost' => (int) presence(env('OSU_RUNNING_COST'), 3141592), // arbritary default >_> 6 + 'sandbox' => get_bool(env('PAYMENT_SANDBOX')) ?? false, 7 + 4 8 'centili' => [ 5 9 'api_key' => env('CENTILI_API_KEY'), 10 + 'conversion_rate' => (float) presence(env('CENTILI_CONVERSION_RATE'), 100), 11 + 'enabled' => get_bool(env('CENTILI_ENABLED')) ?? false, 6 12 'secret_key' => env('CENTILI_SECRET_KEY'), 7 - 'conversion_rate' => (float) presence(env('CENTILI_CONVERSION_RATE'), 100), 8 13 'widget_url' => env('CENTILI_WIDGET_URL'), 9 14 ], 15 + 10 16 'paypal' => [ 11 17 'client_id' => env('PAYPAL_CLIENT_ID'), 12 18 'client_secret' => env('PAYPAL_CLIENT_SECRET'), 19 + 'merchant_id' => env('PAYPAL_MERCHANT_ID'), 13 20 'url' => env('PAYPAL_URL'), 14 - 'merchant_id' => env('PAYPAL_MERCHANT_ID'), 21 + 15 22 'profiles' => [ 16 23 'no_shipping' => env('PAYPAL_NO_SHIPPING_EXPERIENCE_PROFILE_ID'), 17 24 ], 18 25 ], 26 + 19 27 'shopify' => [ 20 28 'webhook_key' => env('SHOPIFY_WEBHOOK_KEY'), 21 29 ], 30 + 22 31 'xsolla' => [ 23 32 'api_key' => env('XSOLLA_API_KEY'), 24 33 'merchant_id' => env('XSOLLA_MERCHANT_ID'), 25 34 'project_id' => (int) env('XSOLLA_PROJECT_ID'), 26 35 'secret_key' => env('XSOLLA_SECRET_KEY'), 27 36 ], 28 - 29 - 'notification_channel' => env('STORE_NOTIFICATION_CHANNEL'), 30 - 'sandbox' => get_bool(env('PAYMENT_SANDBOX')) ?? false, 31 - 'running_cost' => (int) presence(env('OSU_RUNNING_COST'), 3141592), // arbritary default >_> 32 37 ];
+17
database/factories/UserFactory.php
··· 8 8 namespace Database\Factories; 9 9 10 10 use App\Libraries\Fulfillments\ApplySupporterTag; 11 + use App\Libraries\User\CountryChangeTarget; 11 12 use App\Models\Country; 12 13 use App\Models\User; 13 14 use App\Models\UserAccountHistory; 15 + use App\Models\UserCountryHistory; 14 16 use App\Models\UserStatistics\Model as UserStatisticsModel; 15 17 16 18 class UserFactory extends Factory 17 19 { 18 20 const DEFAULT_PASSWORD = 'password'; 21 + 22 + public static function createRecentCountryHistory(User $user, ?string $country, ?int $months): void 23 + { 24 + $months ??= CountryChangeTarget::minMonths(); 25 + $country ??= Country::factory()->create()->getKey(); 26 + $currentMonth = CountryChangeTarget::currentMonth(); 27 + $userId = $user->getKey(); 28 + for ($i = 0; $i < $months; $i++) { 29 + UserCountryHistory::create([ 30 + 'country_acronym' => $country, 31 + 'user_id' => $userId, 32 + 'year_month' => $currentMonth->subMonths($i), 33 + ]); 34 + } 35 + } 19 36 20 37 private static function defaultPasswordHash() 21 38 {
+36
database/migrations/2023_07_20_062848_create_user_country_history.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + declare(strict_types=1); 7 + 8 + use Illuminate\Database\Migrations\Migration; 9 + use Illuminate\Database\Schema\Blueprint; 10 + use Illuminate\Support\Facades\Schema; 11 + 12 + return new class extends Migration 13 + { 14 + /** 15 + * Run the migrations. 16 + */ 17 + public function up(): void 18 + { 19 + Schema::create('user_country_history', function (Blueprint $table) { 20 + $table->unsignedInteger('user_id'); 21 + $table->char('year_month', 4); 22 + $table->char('country_acronym', 2); 23 + $table->unsignedInteger('count')->default(1); 24 + $table->timestamp('last_updated')->useCurrent()->useCurrentOnUpdate(); 25 + $table->primary(['user_id', 'year_month', 'country_acronym']); 26 + }); 27 + } 28 + 29 + /** 30 + * Reverse the migrations. 31 + */ 32 + public function down(): void 33 + { 34 + Schema::dropIfExists('user_country_history'); 35 + } 36 + };
+52 -68
database/mods.json
··· 34 34 "SD", 35 35 "PF", 36 36 "AC", 37 - "AT", 38 - "CN", 39 37 "RX", 40 38 "AP" 41 39 ], ··· 125 123 "NF", 126 124 "PF", 127 125 "TP", 128 - "AT", 129 - "CN", 130 126 "RX", 131 127 "AP" 132 128 ], ··· 150 146 "NF", 151 147 "SD", 152 148 "AC", 153 - "AT", 154 - "CN", 155 149 "RX", 156 150 "AP" 157 151 ], ··· 310 304 "EZ", 311 305 "NF", 312 306 "PF", 313 - "AT", 314 - "CN", 315 307 "RX", 316 308 "AP" 317 309 ], ··· 502 494 "Type": "Automation", 503 495 "Settings": [], 504 496 "IncompatibleMods": [ 505 - "NF", 506 - "SD", 507 - "PF", 508 - "AC", 509 497 "AL", 510 498 "SG", 511 499 "CN", ··· 528 516 "Type": "Automation", 529 517 "Settings": [], 530 518 "IncompatibleMods": [ 531 - "NF", 532 - "SD", 533 - "PF", 534 - "AC", 535 519 "AL", 536 520 "SG", 537 521 "AT", ··· 1025 1009 "UserPlayable": true, 1026 1010 "ValidForMultiplayer": true, 1027 1011 "ValidForMultiplayerAsFreeMod": true 1012 + }, 1013 + { 1014 + "Acronym": "SV2", 1015 + "Name": "Score V2", 1016 + "Description": "Score set on earlier osu! versions with the V2 scoring algorithm active.", 1017 + "Type": "System", 1018 + "Settings": [], 1019 + "IncompatibleMods": [], 1020 + "RequiresConfiguration": false, 1021 + "UserPlayable": true, 1022 + "ValidForMultiplayer": true, 1023 + "ValidForMultiplayerAsFreeMod": true 1028 1024 } 1029 1025 ] 1030 1026 }, ··· 1057 1053 "SD", 1058 1054 "PF", 1059 1055 "AC", 1060 - "AT", 1061 - "CN", 1062 1056 "RX" 1063 1057 ], 1064 1058 "RequiresConfiguration": false, ··· 1145 1139 "IncompatibleMods": [ 1146 1140 "NF", 1147 1141 "PF", 1148 - "AT", 1149 - "CN", 1150 1142 "RX" 1151 1143 ], 1152 1144 "RequiresConfiguration": false, ··· 1169 1161 "NF", 1170 1162 "SD", 1171 1163 "AC", 1172 - "AT", 1173 - "CN", 1174 1164 "RX" 1175 1165 ], 1176 1166 "RequiresConfiguration": false, ··· 1283 1273 "IncompatibleMods": [ 1284 1274 "NF", 1285 1275 "PF", 1286 - "AT", 1287 - "CN", 1288 1276 "RX" 1289 1277 ], 1290 1278 "RequiresConfiguration": false, ··· 1392 1380 "Type": "Automation", 1393 1381 "Settings": [], 1394 1382 "IncompatibleMods": [ 1395 - "NF", 1396 - "SD", 1397 - "PF", 1398 - "AC", 1399 1383 "SG", 1400 1384 "CN", 1401 1385 "RX", ··· 1413 1397 "Type": "Automation", 1414 1398 "Settings": [], 1415 1399 "IncompatibleMods": [ 1416 - "NF", 1417 - "SD", 1418 - "PF", 1419 - "AC", 1420 1400 "SG", 1421 1401 "AT", 1422 1402 "CN", ··· 1570 1550 "UserPlayable": true, 1571 1551 "ValidForMultiplayer": false, 1572 1552 "ValidForMultiplayerAsFreeMod": false 1553 + }, 1554 + { 1555 + "Acronym": "SV2", 1556 + "Name": "Score V2", 1557 + "Description": "Score set on earlier osu! versions with the V2 scoring algorithm active.", 1558 + "Type": "System", 1559 + "Settings": [], 1560 + "IncompatibleMods": [], 1561 + "RequiresConfiguration": false, 1562 + "UserPlayable": true, 1563 + "ValidForMultiplayer": true, 1564 + "ValidForMultiplayerAsFreeMod": true 1573 1565 } 1574 1566 ] 1575 1567 }, ··· 1608 1600 "SD", 1609 1601 "PF", 1610 1602 "AC", 1611 - "AT", 1612 - "CN", 1613 1603 "RX" 1614 1604 ], 1615 1605 "RequiresConfiguration": false, ··· 1694 1684 "IncompatibleMods": [ 1695 1685 "NF", 1696 1686 "PF", 1697 - "AT", 1698 - "CN", 1699 1687 "RX" 1700 1688 ], 1701 1689 "RequiresConfiguration": false, ··· 1718 1706 "NF", 1719 1707 "SD", 1720 1708 "AC", 1721 - "AT", 1722 - "CN", 1723 1709 "RX" 1724 1710 ], 1725 1711 "RequiresConfiguration": false, ··· 1831 1817 "EZ", 1832 1818 "NF", 1833 1819 "PF", 1834 - "AT", 1835 - "CN", 1836 1820 "RX" 1837 1821 ], 1838 1822 "RequiresConfiguration": false, ··· 1911 1895 "Type": "Automation", 1912 1896 "Settings": [], 1913 1897 "IncompatibleMods": [ 1914 - "NF", 1915 - "SD", 1916 - "PF", 1917 - "AC", 1918 1898 "CN", 1919 1899 "RX" 1920 1900 ], ··· 1930 1910 "Type": "Automation", 1931 1911 "Settings": [], 1932 1912 "IncompatibleMods": [ 1933 - "NF", 1934 - "SD", 1935 - "PF", 1936 - "AC", 1937 1913 "AT", 1938 1914 "CN", 1939 1915 "RX" ··· 2081 2057 "UserPlayable": true, 2082 2058 "ValidForMultiplayer": true, 2083 2059 "ValidForMultiplayerAsFreeMod": true 2060 + }, 2061 + { 2062 + "Acronym": "SV2", 2063 + "Name": "Score V2", 2064 + "Description": "Score set on earlier osu! versions with the V2 scoring algorithm active.", 2065 + "Type": "System", 2066 + "Settings": [], 2067 + "IncompatibleMods": [], 2068 + "RequiresConfiguration": false, 2069 + "UserPlayable": true, 2070 + "ValidForMultiplayer": true, 2071 + "ValidForMultiplayerAsFreeMod": true 2084 2072 } 2085 2073 ] 2086 2074 }, ··· 2118 2106 "IncompatibleMods": [ 2119 2107 "SD", 2120 2108 "PF", 2121 - "AC", 2122 - "AT", 2123 - "CN" 2109 + "AC" 2124 2110 ], 2125 2111 "RequiresConfiguration": false, 2126 2112 "UserPlayable": true, ··· 2205 2191 ], 2206 2192 "IncompatibleMods": [ 2207 2193 "NF", 2208 - "PF", 2209 - "AT", 2210 - "CN" 2194 + "PF" 2211 2195 ], 2212 2196 "RequiresConfiguration": false, 2213 2197 "UserPlayable": true, ··· 2228 2212 "IncompatibleMods": [ 2229 2213 "NF", 2230 2214 "SD", 2231 - "AC", 2232 - "AT", 2233 - "CN" 2215 + "AC" 2234 2216 ], 2235 2217 "RequiresConfiguration": false, 2236 2218 "UserPlayable": true, ··· 2373 2355 "IncompatibleMods": [ 2374 2356 "EZ", 2375 2357 "NF", 2376 - "PF", 2377 - "AT", 2378 - "CN" 2358 + "PF" 2379 2359 ], 2380 2360 "RequiresConfiguration": false, 2381 2361 "UserPlayable": true, ··· 2730 2710 "Type": "Automation", 2731 2711 "Settings": [], 2732 2712 "IncompatibleMods": [ 2733 - "NF", 2734 - "SD", 2735 - "PF", 2736 - "AC", 2737 2713 "CN", 2738 2714 "AS" 2739 2715 ], ··· 2749 2725 "Type": "Automation", 2750 2726 "Settings": [], 2751 2727 "IncompatibleMods": [ 2752 - "NF", 2753 - "SD", 2754 - "PF", 2755 - "AC", 2756 2728 "AT", 2757 2729 "CN", 2758 2730 "AS" ··· 2884 2856 "UserPlayable": true, 2885 2857 "ValidForMultiplayer": false, 2886 2858 "ValidForMultiplayerAsFreeMod": false 2859 + }, 2860 + { 2861 + "Acronym": "SV2", 2862 + "Name": "Score V2", 2863 + "Description": "Score set on earlier osu! versions with the V2 scoring algorithm active.", 2864 + "Type": "System", 2865 + "Settings": [], 2866 + "IncompatibleMods": [], 2867 + "RequiresConfiguration": false, 2868 + "UserPlayable": true, 2869 + "ValidForMultiplayer": true, 2870 + "ValidForMultiplayerAsFreeMod": true 2887 2871 } 2888 2872 ] 2889 2873 }
+4
resources/css/bem/account-edit-entry.less
··· 17 17 align-items: center; 18 18 flex-wrap: wrap; 19 19 20 + @media @desktop { 21 + flex-wrap: nowrap; 22 + } 23 + 20 24 &--avatar { 21 25 display: block; 22 26
+2
resources/css/bem/flag-country.less
··· 13 13 border-radius: 3px; 14 14 position: relative; 15 15 filter: saturate(1.1); 16 + display: block; 16 17 17 18 .own-layer(); // Force gpu filter: on Safari. 18 19 ··· 40 41 &--wiki { 41 42 display: inline-block; 42 43 border-radius: unset; // border-radius makes it blurry at smaller sizes 44 + bottom: -0.1em; // more aligned with inlined text (probably) 43 45 } 44 46 }
-4
resources/css/bem/notification-action-button.less
··· 12 12 color: @osu-colour-f1; 13 13 pointer-events: initial; 14 14 15 - .@{_notification}--legacy_pm & { 16 - display: none; 17 - } 18 - 19 15 &:hover { 20 16 color: #fff; 21 17 }
-53
resources/css/bem/osu-page.less
··· 136 136 padding-bottom: 20px; 137 137 } 138 138 139 - &--download { 140 - .page-width(20px); 141 - .default; 142 - 143 - display: flex; 144 - flex-direction: column; 145 - 146 - @media @desktop { 147 - .page-width-desktop(20px); 148 - } 149 - } 150 - 151 139 &--forum { 152 140 background-color: @osu-colour-b5; 153 141 color: @osu-colour-c1; ··· 159 147 color: @osu-colour-c1; 160 148 } 161 149 162 - &--forum-topic-feature-vote { 163 - .default-box-shadow(); 164 - background-color: #fff; 165 - padding: 20px; 166 - margin-bottom: 5px; 167 - } 168 - 169 150 &--forum-topic-reply { 170 151 background-color: @osu-colour-b2; 171 152 color: @osu-colour-c1; ··· 196 177 } 197 178 } 198 179 199 - &--forum-topic-watches-list { 200 - .default(); 201 - padding-top: 10px; 202 - padding-bottom: 10px; 203 - } 204 - 205 180 &--full { 206 181 flex: 1 0 auto; 207 182 } ··· 217 192 .default; 218 193 } 219 194 220 - &--header { 221 - .default; 222 - margin-bottom: 0; 223 - } 224 - 225 - &--header-news, &--groups { 226 - .default-box-shadow(); 227 - background-color: #333; 228 - } 229 - 230 195 &--info-bar { 231 196 .default-gutter-v2(); 232 197 padding-top: 5px; ··· 270 235 } 271 236 } 272 237 273 - &--store-product { 274 - .default-gutter-v2(); 275 - padding-top: 20px; 276 - padding-bottom: 20px; 277 - background-color: @osu-colour-b5; 278 - color: @osu-colour-c1; 279 - } 280 - 281 238 &--supporter { 282 239 .default; 283 240 display: flex; 284 241 flex-direction: column; 285 - } 286 - 287 - &--users { 288 - .default(); 289 - background-color: hsl(var(--hsl-b3)); 290 - margin-bottom: 0; 291 - } 292 - 293 - &--users-show-header { 294 - .default-box-shadow(); 295 242 } 296 243 297 244 &--wiki {
+1 -4
resources/css/bem/profile-badges.less
··· 7 7 gap: 10px; 8 8 9 9 &__badge { 10 - flex: none; 11 10 width: 86px; 12 11 height: 40px; 13 - background-size: contain; 14 - background-position: center; 15 - background-repeat: no-repeat; 12 + object-fit: contain; 16 13 } 17 14 }
+3
resources/css/bem/show-more-link.less
··· 70 70 } 71 71 72 72 &--profile-page { 73 + .default-box-shadow(); 74 + position: sticky; 75 + bottom: 5px; 73 76 margin: 5px auto 0; 74 77 } 75 78
+1 -1
resources/css/utilities.less
··· 19 19 } 20 20 21 21 .u-contents { 22 - display: contents; 22 + display: contents !important; 23 23 } 24 24 25 25 .u-ellipsis-overflow {
-104
resources/js/beatmap-discussions-history/main.coffee
··· 1 - # Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 - # See the LICENCE file in the repository root for full licence text. 3 - 4 - import { Discussion } from 'beatmap-discussions/discussion' 5 - import { BeatmapsContext } from 'beatmap-discussions/beatmaps-context' 6 - import { BeatmapsetsContext } from 'beatmap-discussions/beatmapsets-context' 7 - import { DiscussionsContext } from 'beatmap-discussions/discussions-context' 8 - import { ReviewEditorConfigContext } from 'beatmap-discussions/review-editor-config-context' 9 - import BeatmapsetCover from 'components/beatmapset-cover' 10 - import { deletedUser } from 'models/user' 11 - import * as React from 'react' 12 - import { a, div, img } from 'react-dom-factories' 13 - import { makeUrl } from 'utils/beatmapset-discussion-helper' 14 - import { trans } from 'utils/lang' 15 - import { nextVal } from 'utils/seq' 16 - el = React.createElement 17 - 18 - export class Main extends React.PureComponent 19 - constructor: (props) -> 20 - super props 21 - 22 - @eventId = "beatmapset-discussions-history-#{nextVal()}" 23 - @cache = {} 24 - @state = JSON.parse(props.container.dataset.discussionsState ? null) 25 - @restoredState = @state? 26 - 27 - if !@restoredState 28 - @state = 29 - beatmapsets: props.beatmapsets 30 - discussions: props.discussions 31 - users: props.users 32 - relatedBeatmaps: props.relatedBeatmaps 33 - relatedDiscussions: props.relatedDiscussions 34 - 35 - 36 - componentWillUnmount: => 37 - $(window).stop() 38 - 39 - 40 - discussions: => 41 - # skipped discussions 42 - # - not privileged (deleted discussion) 43 - # - deleted beatmap 44 - @cache.discussions ?= _ @state.relatedDiscussions 45 - .filter (d) -> !_.isEmpty(d) 46 - .keyBy 'id' 47 - .value() 48 - 49 - 50 - beatmaps: => 51 - @cache.beatmaps ?= _.keyBy(this.props.relatedBeatmaps, 'id') 52 - 53 - 54 - beatmapsets: => 55 - @cache.beatmapsets ?= _.keyBy(this.props.beatmapsets, 'id') 56 - 57 - 58 - saveStateToContainer: => 59 - @props.container.dataset.discussionsState = JSON.stringify(@state) 60 - 61 - 62 - render: => 63 - beatmaps = @beatmaps() 64 - beatmapsets = @beatmapsets() 65 - 66 - el ReviewEditorConfigContext.Provider, value: @props.reviewsConfig, 67 - el DiscussionsContext.Provider, value: @discussions(), 68 - el BeatmapsetsContext.Provider, value: beatmapsets, 69 - el BeatmapsContext.Provider, value: beatmaps, 70 - div className: 'modding-profile-list modding-profile-list--index', 71 - if @props.discussions.length == 0 72 - div className: 'modding-profile-list__empty', trans('beatmap_discussions.index.none_found') 73 - else 74 - for discussion in @props.discussions when discussion? 75 - div 76 - className: 'modding-profile-list__row' 77 - key: discussion.id, 78 - 79 - a 80 - className: 'modding-profile-list__thumbnail' 81 - href: makeUrl(discussion: discussion), 82 - 83 - el BeatmapsetCover, 84 - beatmapset: beatmapsets[discussion.beatmapset_id] 85 - size: 'list' 86 - 87 - el Discussion, 88 - discussion: discussion 89 - users: @users() 90 - currentBeatmap: beatmaps[discussion.beatmap_id] 91 - currentUser: currentUser 92 - beatmapset: beatmapsets[discussion.beatmapset_id] 93 - isTimelineVisible: false 94 - readonly: true 95 - showDeleted: true 96 - preview: true 97 - 98 - 99 - users: => 100 - if !@cache.users? 101 - @cache.users = _.keyBy @state.users, 'id' 102 - @cache.users[null] = @cache.users[undefined] = deletedUser.toJson() 103 - 104 - @cache.users
+98
resources/js/beatmap-discussions-history/main.tsx
··· 1 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 + // See the LICENCE file in the repository root for full licence text. 3 + 4 + import { BeatmapsContext } from 'beatmap-discussions/beatmaps-context'; 5 + import { BeatmapsetsContext } from 'beatmap-discussions/beatmapsets-context'; 6 + import { Discussion } from 'beatmap-discussions/discussion'; 7 + import { DiscussionsContext } from 'beatmap-discussions/discussions-context'; 8 + import BeatmapsetCover from 'components/beatmapset-cover'; 9 + import BeatmapsetDiscussionsBundleJson from 'interfaces/beatmapset-discussions-bundle-json'; 10 + import { keyBy } from 'lodash'; 11 + import { computed, makeObservable } from 'mobx'; 12 + import { observer } from 'mobx-react'; 13 + import { deletedUserJson } from 'models/user'; 14 + import * as React from 'react'; 15 + import { makeUrl } from 'utils/beatmapset-discussion-helper'; 16 + import { trans } from 'utils/lang'; 17 + 18 + interface Props { 19 + bundle: BeatmapsetDiscussionsBundleJson; 20 + } 21 + 22 + @observer 23 + export default class Main extends React.Component<Props> { 24 + @computed 25 + private get beatmaps() { 26 + return keyBy(this.props.bundle.beatmaps, 'id'); 27 + } 28 + 29 + @computed 30 + private get beatmapsets() { 31 + return keyBy(this.props.bundle.beatmapsets, 'id'); 32 + } 33 + 34 + @computed 35 + private get discussions() { 36 + return keyBy(this.props.bundle.included_discussions, 'id'); 37 + } 38 + 39 + @computed 40 + private get users() { 41 + const values = keyBy(this.props.bundle.users, 'id'); 42 + // eslint-disable-next-line id-blacklist 43 + values.null = values.undefined = deletedUserJson; 44 + 45 + return values; 46 + } 47 + 48 + constructor(props: Props) { 49 + super(props); 50 + 51 + makeObservable(this); 52 + } 53 + 54 + render() { 55 + return ( 56 + <DiscussionsContext.Provider value={this.discussions}> 57 + <BeatmapsetsContext.Provider value={this.beatmapsets}> 58 + <BeatmapsContext.Provider value={this.beatmaps}> 59 + <div className='modding-profile-list modding-profile-list--index'> 60 + {this.props.bundle.discussions.length === 0 ? ( 61 + <div className='modding-profile-list__empty'> 62 + {trans('beatmap_discussions.index.none_found')} 63 + </div> 64 + ) : (this.props.bundle.discussions.map((discussion) => { 65 + // TODO: handle in child component? Refactored state might not have beatmapset here (and uses Map) 66 + const beatmapset = this.beatmapsets[discussion.beatmapset_id]; 67 + 68 + return beatmapset != null && ( 69 + <div key={discussion.id} className='modding-profile-list__row'> 70 + <a 71 + className='modding-profile-list__thumbnail' 72 + href={makeUrl({ discussion })} 73 + > 74 + <BeatmapsetCover 75 + beatmapset={beatmapset} 76 + size='list' 77 + /> 78 + </a> 79 + <Discussion 80 + beatmapset={beatmapset} 81 + currentBeatmap={discussion.beatmap_id != null ? this.beatmaps[discussion.beatmap_id] : null} 82 + discussion={discussion} 83 + isTimelineVisible={false} 84 + preview 85 + readonly 86 + showDeleted 87 + users={this.users} 88 + /> 89 + </div> 90 + ); 91 + }))} 92 + </div> 93 + </BeatmapsContext.Provider> 94 + </BeatmapsetsContext.Provider> 95 + </DiscussionsContext.Provider> 96 + ); 97 + } 98 + }
+1 -3
resources/js/beatmap-discussions/beatmaps-owner-editor.tsx
··· 5 5 import UserJson from 'interfaces/user-json'; 6 6 import { makeObservable, observable } from 'mobx'; 7 7 import { observer } from 'mobx-react'; 8 - import { deletedUser, normaliseUsername } from 'models/user'; 8 + import { deletedUserJson, normaliseUsername } from 'models/user'; 9 9 import * as React from 'react'; 10 10 import { group as groupBeatmaps } from 'utils/beatmap-helper'; 11 11 import { trans } from 'utils/lang'; ··· 16 16 onClose: () => void; 17 17 users: Partial<Record<number, UserJson>>; 18 18 } 19 - 20 - const deletedUserJson = deletedUser.toJson(); 21 19 22 20 @observer 23 21 export default class BeatmapsOwnerEditor extends React.Component<Props> {
+3 -3
resources/js/beatmap-discussions/discussion.tsx
··· 9 9 import { findLast } from 'lodash'; 10 10 import { action, computed, makeObservable } from 'mobx'; 11 11 import { observer } from 'mobx-react'; 12 - import { deletedUser } from 'models/user'; 12 + import { deletedUserJson } from 'models/user'; 13 13 import core from 'osu-core-singleton'; 14 14 import * as React from 'react'; 15 15 import { badgeGroup, canModeratePosts, formatTimestamp, makeUrl, startingPost } from 'utils/beatmapset-discussion-helper'; ··· 114 114 115 115 this.lastResolvedState = false; 116 116 117 - const user = this.props.users[this.props.discussion.user_id] ?? deletedUser.toJson(); 117 + const user = this.props.users[this.props.discussion.user_id] ?? deletedUserJson; 118 118 const group = badgeGroup({ 119 119 beatmapset: this.props.beatmapset, 120 120 currentBeatmap: this.props.currentBeatmap, ··· 213 213 } 214 214 215 215 private renderPost(post: BeatmapsetDiscussionPostJson, type: 'discussion' | 'reply') { 216 - const user = this.props.users[post.user_id] ?? deletedUser.toJson(); 216 + const user = this.props.users[post.user_id] ?? deletedUserJson; 217 217 218 218 if (post.system) { 219 219 return (
+2 -2
resources/js/beatmap-discussions/main.coffee
··· 7 7 import { ReviewEditorConfigContext } from 'beatmap-discussions/review-editor-config-context' 8 8 import BackToTop from 'components/back-to-top' 9 9 import { route } from 'laroute' 10 - import { deletedUser } from 'models/user' 10 + import { deletedUserJson } from 'models/user' 11 11 import core from 'osu-core-singleton' 12 12 import * as React from 'react' 13 13 import { div } from 'react-dom-factories' ··· 515 515 users: => 516 516 if !@cache.users? 517 517 @cache.users = _.keyBy @state.beatmapset.related_users, 'id' 518 - @cache.users[null] = @cache.users[undefined] = deletedUser.toJson() 518 + @cache.users[null] = @cache.users[undefined] = deletedUserJson 519 519 520 520 @cache.users 521 521
-9
resources/js/beatmap-discussions/nominations.tsx
··· 30 30 import { classWithModifiers } from 'utils/css'; 31 31 import { formatNumber } from 'utils/html'; 32 32 import { joinComponents, trans, transExists } from 'utils/lang'; 33 - import { pageChange } from 'utils/page-change'; 34 33 import { presence } from 'utils/string'; 35 34 import { wikiUrl } from 'utils/url'; 36 35 import CurrentDiscussions from './current-discussions'; ··· 85 84 super(props); 86 85 87 86 makeObservable(this); 88 - } 89 - 90 - componentDidMount() { 91 - pageChange(); 92 - } 93 - 94 - componentDidUpdate() { 95 - pageChange(); 96 87 } 97 88 98 89 componentWillUnmount() {
+2 -2
resources/js/beatmap-discussions/post.tsx
··· 22 22 import { isEqual } from 'lodash'; 23 23 import { action, autorun, computed, makeObservable, observable, runInAction } from 'mobx'; 24 24 import { disposeOnUnmount, observer } from 'mobx-react'; 25 - import { deletedUser } from 'models/user'; 25 + import { deletedUser, deletedUserJson } from 'models/user'; 26 26 import core from 'osu-core-singleton'; 27 27 import * as React from 'react'; 28 28 import TextareaAutosize from 'react-autosize-textarea'; ··· 247 247 return null; 248 248 } 249 249 250 - const lastEditor = this.props.users[this.props.post.last_editor_id] ?? deletedUser.toJson(); 250 + const lastEditor = this.props.users[this.props.post.last_editor_id] ?? deletedUserJson; 251 251 252 252 return ( 253 253 <span className={`${bn}__info`}>
+12 -10
resources/js/components/comment.tsx
··· 127 127 128 128 @computed 129 129 private get user() { 130 - return this.getUser(this.props.comment.userId); 130 + return this.getCommentUser(this.props.comment); 131 131 } 132 132 133 133 constructor(props: Props) { ··· 168 168 ); 169 169 } 170 170 171 - private getUser(id: number | null | undefined): UserJson | { username: string } { 172 - const user = id == null ? null : userStore.get(id)?.toJson(); 173 - 174 - return user == null 175 - ? this.props.comment.legacyName == null 171 + private getCommentUser(comment: CommentModel): UserJson | { username: string } { 172 + return this.getUser(comment.userId) ?? ( 173 + comment.legacyName == null 176 174 ? deletedUser 177 - : { username: this.props.comment.legacyName } 178 - : user; 175 + : { username: comment.legacyName } 176 + ); 177 + } 178 + 179 + private getUser(id: number | null | undefined) { 180 + return id == null ? undefined : userStore.get(id)?.toJson(); 179 181 } 180 182 181 183 @action ··· 437 439 <StringWithComponent 438 440 mappings={{ 439 441 timeago: <TimeWithTooltip dateTime={this.props.comment.editedAt} relative />, 440 - user: <UserLink user={this.getUser(this.props.comment.editedById)} />, 442 + user: <UserLink user={this.getUser(this.props.comment.editedById) ?? deletedUser} />, 441 443 }} 442 444 pattern={trans('comments.edited')} 443 445 /> ··· 614 616 615 617 if (parent == null) return; 616 618 617 - const parentUser = this.getUser(parent.userId); 619 + const parentUser = this.getCommentUser(parent); 618 620 619 621 const content = ( 620 622 <>
+1 -1
resources/js/components/flag-country.tsx
··· 25 25 } 26 26 27 27 return ( 28 - <div 28 + <span 29 29 className={classWithModifiers('flag-country', modifiers)} 30 30 style={{ 31 31 backgroundImage: `url('${flagUrl(country.code)}')`,
+1 -5
resources/js/components/main-notification-icon.tsx
··· 21 21 return types.reduce((acc, current) => acc + core.dataStore.notificationStore.unreadStacks.getOrCreateType({ objectType: current }).total, 0); 22 22 } 23 23 24 - private get unreadLegacyPmCount() { 25 - return core.currentUser?.unread_pm_count ?? 0; 26 - } 27 - 28 24 constructor(props: Props) { 29 25 super(props); 30 26 ··· 33 29 34 30 render() { 35 31 return (<NotificationIcon 36 - count={this.unreadCount + this.unreadLegacyPmCount} 32 + count={this.unreadCount} 37 33 iconClassName='fas fa-bell' 38 34 ready={core.notificationsWorker.hasData} 39 35 type={this.props.type}
+1 -1
resources/js/components/notification-banner.tsx
··· 51 51 } 52 52 53 53 private notifySyncHeight(this: void) { 54 - $.publish('osu:page:change'); 54 + $.publish('sync-height:force'); 55 55 } 56 56 }
+1 -1
resources/js/components/profile-page-kudosu.tsx
··· 150 150 <ul className='profile-extra-entries profile-extra-entries--kudosu'> 151 151 {this.kudosu.items.map((kudosu) => <Entry key={kudosu.id} kudosu={kudosu} />)} 152 152 153 - <li className='profile-extra-entries__item'> 153 + <li className='profile-extra-entries__item u-contents'> 154 154 <ShowMoreLink 155 155 {...this.kudosu.pagination} 156 156 callback={this.handleShowMore}
+1 -1
resources/js/contest-entry/uploader.coffee
··· 73 73 file = data.files[0] 74 74 extension = /(\.[^.]+)$/.exec(file.name)[1] 75 75 76 - if !_.includes(allowedExtensions, extension) 76 + if !_.includes(allowedExtensions, extension.toLowerCase()) 77 77 popup trans("contest.entry.wrong_type.#{@props.contest.type}"), 'danger' 78 78 return 79 79
+2 -4
resources/js/core-legacy/bbcode-preview.coffee
··· 3 3 4 4 import { route } from 'laroute' 5 5 import { emitError } from 'utils/ajax' 6 - import { pageChange } from 'utils/page-change' 7 6 import { present } from 'utils/string' 8 7 9 8 export default class BbcodePreview ··· 40 39 $body.attr('data-last-text', text) 41 40 42 41 $preview.html(data) 43 - pageChange() 44 42 @showPreview(e) 45 43 46 44 .fail emitError(target) ··· 48 46 49 47 showPreview: (e) => 50 48 $(e.target).parents('.js-bbcode-preview--form').attr('data-state', 'preview') 51 - pageChange() # sync height of reply box 49 + $.publish 'sync-height:force' 52 50 53 51 54 52 hidePreview: (e) => 55 53 $form = $(e.target).parents('.js-bbcode-preview--form') 56 54 $form.attr('data-state', 'write') 57 - pageChange() # sync height of reply box 55 + $.publish 'sync-height:force' 58 56 59 57 $form.find('.js-bbcode-preview--body').focus()
-2
resources/js/core-legacy/current-user-observer.coffee
··· 10 10 constructor: -> 11 11 @covers = document.getElementsByClassName('js-current-user-cover') 12 12 @avatars = document.getElementsByClassName('js-current-user-avatar') 13 - @throttledReinit = _.throttle @reinit, 100 14 13 15 14 $.subscribe 'user:update', @setData 16 15 $(document).on 'turbolinks:load', @reinit 17 - $.subscribe 'osu:page:change', @throttledReinit 18 16 $.subscribe 'user:followUserMapping:update', @updateFollowUserMapping 19 17 20 18 # one time setup to monitor cover url variable. No disposer because nothing destroys this object.
-2
resources/js/core-legacy/forum-auto-click.coffee
··· 29 29 30 30 31 31 onLoad: => 32 - $.unsubscribe 'osu:page:change', @throttledOnScroll 33 32 window.removeEventListener 'scroll', @throttledOnScroll 34 33 35 34 @nextLink = document.querySelector('.js-forum__posts-show-more--next') ··· 37 36 38 37 if @nextLink? && @previousLink? 39 38 @throttledOnScroll() 40 - $.subscribe 'osu:page:change', @throttledOnScroll 41 39 window.addEventListener 'scroll', @throttledOnScroll 42 40 43 41
-3
resources/js/core-legacy/forum-topic-reply.coffee
··· 1 1 # Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 2 # See the LICENCE file in the repository root for full licence text. 3 3 4 - import { pageChange } from 'utils/page-change' 5 4 import { currentUrl, navigate } from 'utils/turbolinks' 6 5 7 6 export default class ForumTopicReply ··· 113 112 else 114 113 @forum.setTotalPosts(@forum.totalPosts() + 1) 115 114 @forum.endPost().insertAdjacentHTML 'afterend', data 116 - pageChange() 117 115 118 116 @forum.endPost().scrollIntoView() 119 117 ··· 169 167 target.insertBefore(box, target.firstChild) 170 168 171 169 $input.focus() if inputFocused 172 - pageChange() # sync reply box height
-3
resources/js/core-legacy/forum.coffee
··· 6 6 import { blackoutVisible } from 'utils/blackout' 7 7 import { bottomPage, formatNumber, isInputElement } from 'utils/html' 8 8 import { hideLoadingOverlay } from 'utils/loading-overlay' 9 - import { pageChange } from 'utils/page-change' 10 9 import { present } from 'utils/string' 11 10 import { currentUrl } from 'utils/turbolinks' 12 11 ··· 37 36 @maxPosts = 250 38 37 39 38 $(document).on 'turbolinks:load', @throttledBoot 40 - $.subscribe 'osu:page:change', @throttledBoot 41 39 42 40 $(window).on 'scroll', @refreshCounter 43 41 $(document).on 'click', '.js-forum-posts-show-more', @showMore ··· 333 331 targetDocumentScrollTop = currentDocumentScrollTop + currentScrollReferenceTop - scrollReferenceTop 334 332 window.scrollTo x, targetDocumentScrollTop 335 333 336 - pageChange() 337 334 link.dataset.failed = '0' 338 335 339 336 .always ->
-2
resources/js/core-legacy/nav2.coffee
··· 3 3 4 4 import { blackoutHide, blackoutShow } from 'utils/blackout' 5 5 import { fadeToggle } from 'utils/fade' 6 - import { pageChangeImmediate } from 'utils/page-change' 7 6 8 7 export default class Nav2 9 8 constructor: (@clickMenu) -> ··· 38 37 @centerPopup currentPopup, link 39 38 40 39 $(window).on 'resize.nav2-center-popup', doCenter 41 - pageChangeImmediate() if @loginBoxVisible() 42 40 doCenter() 43 41 currentPopup.querySelector('.js-nav2--autofocus')?.focus() 44 42
-2
resources/js/core-legacy/post-preview.coffee
··· 2 2 # See the LICENCE file in the repository root for full licence text. 3 3 4 4 import { route } from 'laroute' 5 - import { pageChange } from 'utils/page-change' 6 5 7 6 export default class PostPreview 8 7 constructor: -> ··· 38 37 $preview.html data 39 38 $preview.attr 'data-raw', body 40 39 $previewBox.removeClass 'hidden' 41 - pageChange()
-1
resources/js/core-legacy/sticky-footer.coffee
··· 17 17 $(window).on 'scroll resize', @stickOrUnstick 18 18 $.subscribe 'stickyFooter:check', @throttledStickOrUnstick 19 19 $(document).on 'turbolinks:load', @throttledStickOrUnstick 20 - $.subscribe 'osu:page:change', @throttledStickOrUnstick 21 20 22 21 23 22 stickOrUnstick: =>
-1
resources/js/core-legacy/sync-height.coffee
··· 8 8 @throttledSync = _.throttle @sync, 100 9 9 10 10 $(document).on 'turbolinks:load', @sync 11 - $.subscribe 'osu:page:change', @throttledSync 12 11 $.subscribe 'sync-height:force', @sync 13 12 $(window).on 'resize', @sync 14 13
-8
resources/js/core/forum/forum-post-edit.ts
··· 1 1 // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 2 // See the LICENCE file in the repository root for full licence text. 3 3 4 - import { pageChange } from 'utils/page-change'; 5 - 6 4 export default class ForumPostEdit { 7 5 constructor() { 8 6 $(document) ··· 21 19 $postBox 22 20 .html($postBox.attr('data-original-post') ?? '') 23 21 .attr('data-original-post', null); 24 - 25 - pageChange(); 26 22 }; 27 23 28 24 private handleEditSaved = (e: JQuery.TriggeredEvent, data: string) => { ··· 49 45 } 50 46 51 47 $(target).parents('.js-forum-post').replaceWith(data); 52 - 53 - pageChange(); 54 48 }; 55 49 56 50 private start = (target: unknown, data: string) => { ··· 67 61 .focus(); 68 62 69 63 $.publish('forum-post-input:restore', [$postBox[0]]); 70 - 71 - pageChange(); 72 64 }; 73 65 }
+60 -48
resources/js/core/osu-audio/main.ts
··· 2 2 // See the LICENCE file in the repository root for full licence text. 3 3 4 4 import UserPreferences from 'core/user/user-preferences'; 5 - import { autorun } from 'mobx'; 5 + import { action, autorun, makeObservable } from 'mobx'; 6 6 import { trans } from 'utils/lang'; 7 7 import { presence } from 'utils/string'; 8 8 import Slider from './slider'; ··· 86 86 'NotSupportedError', 87 87 ]; 88 88 89 - audio = new Audio(); 89 + readonly audio = new Audio(); 90 90 private currentSlider?: Slider; 91 91 private durationFormatted = "'0:00'"; 92 92 private hasWorkingVolumeControl = true; ··· 102 102 private url?: string; 103 103 104 104 constructor(private userPreferences: UserPreferences) { 105 + makeObservable(this); 106 + 105 107 this.audio.volume = 0; 106 108 this.audio.addEventListener('pause', this.onPause); 107 109 this.audio.addEventListener('playing', this.onPlaying); ··· 109 111 this.audio.addEventListener('timeupdate', this.onTimeupdate); 110 112 this.audio.addEventListener('volumechange', this.syncVolumeDisplay); 111 113 112 - $(document).on('click', '.js-audio--play', this.onClickPlay); 113 - $(document).on('click', '.js-audio--main-play', this.togglePlay); 114 - $(document).on(Slider.startEvents, '.js-audio--seek', this.onSeekStart); 115 - $(document).on(Slider.startEvents, '.js-audio--volume', this.onVolumeChangeStart); 116 - $(document).on('click', '.js-audio--toggle-mute', this.toggleMute); 117 - $(document).on('click', '.js-audio--toggle-autoplay', this.toggleAutoplay); 118 - $(document).on('click', '.js-audio--nav', this.nav); 119 - $(document).on('turbolinks:load', this.onDocumentReady); 114 + $(document) 115 + .on('click', '.js-audio--play', this.onClickPlay) 116 + .on('click', '.js-audio--main-play', this.togglePlay) 117 + .on(Slider.startEvents, '.js-audio--seek', this.onSeekStart) 118 + .on(Slider.startEvents, '.js-audio--volume', this.onVolumeChangeStart) 119 + .on('click', '.js-audio--toggle-mute', this.toggleMute) 120 + .on('click', '.js-audio--toggle-autoplay', this.toggleAutoplay) 121 + .on('click', '.js-audio--nav', this.nav); 122 + document.addEventListener('turbolinks:load', this.onDocumentReady); 120 123 } 121 124 122 - private checkVolumeSettings = () => { 125 + private readonly checkVolumeSettings = () => { 123 126 const prevVolume = this.audio.volume; 124 127 const testVolume = prevVolume === 0.1 ? 0.2 : 0.1; 125 128 this.audio.volume = testVolume; ··· 133 136 }, 0); 134 137 }; 135 138 136 - private ensurePagePlayerIsAttached = () => { 139 + private readonly ensurePagePlayerIsAttached = () => { 137 140 if (this.pagePlayer != null && !document.body.contains(this.pagePlayer)) { 138 141 this.pagePlayer = undefined; 139 142 } ··· 147 150 } 148 151 } 149 152 150 - private load = (player: HTMLElement) => { 153 + private readonly load = (player: HTMLElement) => { 151 154 const url = player.dataset.audioUrl; 152 155 153 156 if (url == null) { ··· 169 172 // old api returns undefined 170 173 promise?.catch((error: { name: string }) => { 171 174 if (Main.ignoredErrors.includes(error.name)) { 172 - console.debug('playback failed:', error.name); 175 + console.error('playback failed:', error.name); 173 176 this.stop(); 174 177 return; 175 178 } ··· 179 182 this.setNavigation(); 180 183 }; 181 184 182 - private nav = (e: JQuery.ClickEvent) => { 185 + private readonly nav = (e: JQuery.ClickEvent) => { 183 186 const button: unknown = e.currentTarget; 184 187 185 188 if (!(button instanceof HTMLElement)) return; ··· 191 194 } 192 195 }; 193 196 194 - private observePage = (mutations: MutationRecord[]) => { 197 + private readonly observePage = (mutations: MutationRecord[]) => { 195 198 this.ensurePagePlayerIsAttached(); 196 199 const audioElems: HTMLAudioElement[] = []; 197 200 const newPlayers: HTMLElement[] = []; ··· 225 228 this.reattachPagePlayer(newPlayers); 226 229 }; 227 230 228 - private onClickPlay = (e: JQuery.ClickEvent<Document, unknown, HTMLElement, HTMLElement>) => { 231 + private readonly onClickPlay = (e: JQuery.ClickEvent<Document, unknown, HTMLElement, HTMLElement>) => { 229 232 e.preventDefault(); 230 233 231 234 const pagePlayer = this.findPlayer(e.currentTarget); ··· 241 244 } 242 245 }; 243 246 244 - private onDocumentReady = () => { 247 + private readonly onDocumentReady = () => { 245 248 if (this.mainPlayer == null) { 246 249 const mainPlayerPlaceholder = document.querySelector('.js-audio--main'); 247 250 248 251 if (mainPlayerPlaceholder == null) { 249 - console.debug('page is missing main player placeholder'); 252 + console.error('page is missing main player placeholder'); 250 253 return; 251 254 } 252 255 ··· 254 257 mainPlayerPlaceholder.replaceWith(this.mainPlayer); 255 258 256 259 // This requires currentUser and should only be run once so it's done in here. 257 - autorun(() => this.audio.muted = this.userPreferences.get('audio_muted')); 258 - autorun(() => this.audio.volume = this.userPreferences.get('audio_volume')); 260 + autorun(() => { 261 + this.audio.muted = this.userPreferences.get('audio_muted'); 262 + this.audio.volume = this.userPreferences.get('audio_volume'); 263 + 264 + const autoplay = this.userPreferences.get('audio_autoplay') ? '1' : '0'; 265 + if (this.mainPlayer != null) { 266 + this.mainPlayer.dataset.audioAutoplay = autoplay; 267 + } 268 + }); 259 269 260 270 // Only check after initial volume is set otherwise it'll be replaced with the volume at current point 261 271 // due to the check being async. ··· 272 282 this.reattachPagePlayer(); 273 283 }; 274 284 275 - private onEnded = () => { 285 + @action 286 + private readonly onEnded = () => { 276 287 this.stop(); 277 288 278 289 if (this.playerNext != null && this.userPreferences.get('audio_autoplay')) { ··· 280 291 } 281 292 }; 282 293 283 - private onPause = () => { 294 + private readonly onPause = () => { 284 295 this.setState('paused'); 285 296 }; 286 297 287 - private onPlaying = () => { 298 + private readonly onPlaying = () => { 288 299 this.setTimeFormat(); 289 300 this.durationFormatted = format(this.audio.duration, this.timeFormat); 290 301 this.setState('playing'); 291 302 }; 292 303 293 - private onSeekEnd = (slider: Slider) => { 304 + private readonly onSeekEnd = (slider: Slider) => { 294 305 this.currentSlider = undefined; 295 306 const targetTime = slider.getPercentage() === 1 296 307 ? this.audio.duration - 0.01 ··· 299 310 this.setTime(targetTime); 300 311 }; 301 312 302 - private onSeekStart = (e: JQuery.TouchStartEvent) => { 313 + private readonly onSeekStart = (e: JQuery.TouchStartEvent) => { 303 314 const bar: unknown = e.currentTarget; 304 315 305 316 if (!(bar instanceof HTMLElement)) return; ··· 315 326 }); 316 327 }; 317 328 318 - private onTimeupdate = () => { 329 + private readonly onTimeupdate = () => { 319 330 // time update when playing is already handled by a requestAnimationFrame loop 320 331 if (this.audio.paused) { 321 332 this.syncProgress(); 322 333 } 323 334 }; 324 335 325 - private onVolumeChangeEnd = () => { 336 + @action 337 + private readonly onVolumeChangeEnd = () => { 326 338 this.currentSlider = undefined; 327 339 void this.userPreferences.set('audio_volume', this.audio.volume); 328 340 }; 329 341 330 - private onVolumeChangeMove = (slider: Slider) => { 342 + private readonly onVolumeChangeMove = (slider: Slider) => { 331 343 this.audio.volume = slider.getPercentage(); 332 344 }; 333 345 334 - private onVolumeChangeStart = (e: JQuery.TouchStartEvent) => { 346 + private readonly onVolumeChangeStart = (e: JQuery.TouchStartEvent) => { 335 347 const bar: unknown = e.currentTarget; 336 348 337 349 if (!(bar instanceof HTMLElement)) return; ··· 344 356 }); 345 357 }; 346 358 347 - private reattachPagePlayer = (elems?: Element[]) => { 359 + private readonly reattachPagePlayer = (elems?: Element[]) => { 348 360 this.ensurePagePlayerIsAttached(); 349 361 350 362 if (this.url != null && this.pagePlayer == null) { ··· 364 376 this.setNavigation(); 365 377 }; 366 378 367 - private replaceAudioElem = (elem: HTMLAudioElement) => { 379 + private readonly replaceAudioElem = (elem: HTMLAudioElement) => { 368 380 const src = presence(elem.src) ?? presence(elem.querySelector('source')?.src); 369 381 370 382 if (src == null) { ··· 380 392 return player; 381 393 }; 382 394 383 - private replaceAudioElems = (elems?: HTMLAudioElement[]) => { 395 + private readonly replaceAudioElems = (elems?: HTMLAudioElement[]) => { 384 396 if (elems == null) { 385 397 elems = [...document.querySelectorAll('audio')]; 386 398 } ··· 388 400 return elems.map(this.replaceAudioElem); 389 401 }; 390 402 391 - private setNavigation = () => { 403 + private readonly setNavigation = () => { 392 404 if (this.settingNavigation) { 393 405 return; 394 406 } ··· 431 443 }); 432 444 }; 433 445 434 - private setState = (state: PlayState) => { 446 + private readonly setState = (state: PlayState) => { 435 447 this.state = state; 436 448 this.syncState(); 437 449 ··· 449 461 } 450 462 }; 451 463 452 - private setTime = (t: number) => { 464 + private readonly setTime = (t: number) => { 453 465 this.audio.currentTime = t; 454 466 this.syncProgress(); 455 467 }; 456 468 457 - private setTimeFormat = () => { 469 + private readonly setTimeFormat = () => { 458 470 if (this.audio.duration < 600) { 459 471 this.timeFormat = 'minute_minimal'; 460 472 } else if (this.audio.duration < 3600) { ··· 466 478 } 467 479 }; 468 480 469 - private stop = () => { 481 + private readonly stop = () => { 470 482 this.audio.pause(); 471 483 this.currentSlider?.end(); 472 484 this.audio.currentTime = 0; ··· 474 486 this.onPause(); 475 487 }; 476 488 477 - private syncProgress = () => { 489 + private readonly syncProgress = () => { 478 490 if (this.audio.duration > 0) { 479 491 const progress = this.audio.currentTime / this.audio.duration; 480 492 const over50 = progress >= 0.5 ? '1' : '0'; ··· 492 504 } 493 505 }; 494 506 495 - private syncState = () => { 507 + private readonly syncState = () => { 496 508 this.updatePlayers((player) => { 497 - player.dataset.audioAutoplay = this.userPreferences.get('audio_autoplay') ? '1' : '0'; 498 509 player.dataset.audioHasDuration = Number.isFinite(this.audio.duration) ? '1' : '0'; 499 510 player.dataset.audioState = this.state; 500 511 player.dataset.audioTimeFormat = this.timeFormat; ··· 505 516 this.syncVolumeDisplay(); 506 517 }; 507 518 508 - private syncVolumeDisplay = () => { 519 + private readonly syncVolumeDisplay = () => { 509 520 if (this.mainPlayer == null) return; 510 521 511 522 this.mainPlayer.dataset.audioVolumeBarVisible = this.hasWorkingVolumeControl ? '1' : '0'; ··· 513 524 this.mainPlayer.style.setProperty('--volume', this.audio.volume.toString()); 514 525 }; 515 526 516 - private toggleAutoplay = () => { 527 + @action 528 + private readonly toggleAutoplay = () => { 517 529 void this.userPreferences.set('audio_autoplay', !this.userPreferences.get('audio_autoplay')); 518 - this.syncState(); 519 530 }; 520 531 521 - private toggleMute = () => { 532 + @action 533 + private readonly toggleMute = () => { 522 534 void this.userPreferences.set('audio_muted', !this.userPreferences.get('audio_muted')); 523 535 }; 524 536 525 - private togglePlay = () => { 537 + private readonly togglePlay = () => { 526 538 if (this.url == null) { 527 539 return; 528 540 } ··· 534 546 } 535 547 }; 536 548 537 - private updatePlayers = (func: (player: HTMLElement) => void) => { 549 + private readonly updatePlayers = (func: (player: HTMLElement) => void) => { 538 550 [this.mainPlayer, this.pagePlayer].forEach((player) => { 539 551 if (player != null) { 540 552 func(player); ··· 542 554 }); 543 555 }; 544 556 545 - private volumeIcon = () => { 557 + private readonly volumeIcon = () => { 546 558 if (this.audio.muted) { 547 559 return 'muted'; 548 560 } else {
-1
resources/js/core/sticky-header.ts
··· 67 67 constructor() { 68 68 $(window).on('scroll', this.onScroll); 69 69 $(document).on('turbolinks:load', this.debouncedOnScroll); 70 - $.subscribe('osu:page:change', this.debouncedOnScroll); 71 70 $(window).on('resize', this.stickOrUnstick); 72 71 } 73 72
-4
resources/js/dispatcher.ts
··· 6 6 7 7 export default class Dispatcher { 8 8 private listeners = new Set<DispatchListener>(); 9 - private trace = false; 10 9 11 10 get size() { 12 11 return this.listeners.size; ··· 17 16 } 18 17 19 18 dispatch = (action: DispatcherAction) => { 20 - if (this.trace) { 21 - console.debug('Dispatcher::dispatch', action); 22 - } 23 19 this.listeners.forEach((listener) => { 24 20 listener.handleDispatchAction(action); 25 21 });
-20
resources/js/entrypoints/beatmap-discussions-history.coffee
··· 1 - # Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 - # See the LICENCE file in the repository root for full licence text. 3 - 4 - import core from 'osu-core-singleton' 5 - import { createElement } from 'react' 6 - import { parseJson } from 'utils/json' 7 - import { Main } from 'beatmap-discussions-history/main' 8 - 9 - core.reactTurbolinks.register 'beatmap-discussions-history', (container) -> 10 - bundle = parseJson 'json-index' 11 - 12 - # TODO: rename props to match 13 - createElement Main, 14 - beatmapsets: bundle.beatmapsets 15 - discussions: bundle.discussions 16 - users: bundle.users 17 - relatedBeatmaps: bundle.beatmaps 18 - relatedDiscussions: bundle.included_discussions 19 - reviewsConfig: bundle.reviews_config 20 - container: container
+12
resources/js/entrypoints/beatmap-discussions-history.tsx
··· 1 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 + // See the LICENCE file in the repository root for full licence text. 3 + 4 + import Main from 'beatmap-discussions-history/main'; 5 + import BeatmapsetDiscussionsBundleJson from 'interfaces/beatmapset-discussions-bundle-json'; 6 + import core from 'osu-core-singleton'; 7 + import React from 'react'; 8 + import { parseJson } from 'utils/json'; 9 + 10 + core.reactTurbolinks.register('beatmap-discussions-history', () => ( 11 + <Main bundle={parseJson<BeatmapsetDiscussionsBundleJson>('json-index')} /> 12 + ));
+15
resources/js/interfaces/beatmapset-discussions-bundle-json.ts
··· 1 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 + // See the LICENCE file in the repository root for full licence text. 3 + 4 + import BeatmapExtendedJson from './beatmap-extended-json'; 5 + import { BeatmapsetDiscussionJsonForBundle } from './beatmapset-discussion-json'; 6 + import BeatmapsetExtendedJson from './beatmapset-extended-json'; 7 + import UserJson from './user-json'; 8 + 9 + export default interface BeatmapsetDiscussionsBundleJson { 10 + beatmaps: BeatmapExtendedJson[]; 11 + beatmapsets: BeatmapsetExtendedJson[]; 12 + discussions: BeatmapsetDiscussionJsonForBundle[]; 13 + included_discussions: BeatmapsetDiscussionJsonForBundle[]; 14 + users: UserJson[]; 15 + }
+2 -5
resources/js/modding-profile/main.tsx
··· 20 20 import { action, computed, makeObservable, observable } from 'mobx'; 21 21 import { observer } from 'mobx-react'; 22 22 import Kudosu from 'modding-profile/kudosu'; 23 - import { deletedUser } from 'models/user'; 23 + import { deletedUserJson } from 'models/user'; 24 24 import core from 'osu-core-singleton'; 25 25 import Badges from 'profile-page/badges'; 26 26 import Cover from 'profile-page/cover'; ··· 28 28 import headerLinks from 'profile-page/header-links'; 29 29 import * as React from 'react'; 30 30 import { bottomPage } from 'utils/html'; 31 - import { pageChange } from 'utils/page-change'; 32 31 import { nextVal } from 'utils/seq'; 33 32 import { switchNever } from 'utils/switch-never'; 34 33 import { currentUrl } from 'utils/turbolinks'; ··· 122 121 private get users() { 123 122 const values = keyBy(this.props.users, 'id'); 124 123 // eslint-disable-next-line id-blacklist 125 - values.null = values.undefined = deletedUser.toJson(); 124 + values.null = values.undefined = deletedUserJson; 126 125 127 126 return values; 128 127 } ··· 136 135 componentDidMount() { 137 136 // pageScan does not need to run at 144 fps... 138 137 $(window).on(`scroll.${this.eventId}`, throttle(() => this.pageScan(), 20)); 139 - 140 - pageChange(); 141 138 142 139 const page = validPage(currentUrl().hash.slice(1)) ?? 'main'; 143 140
+2 -2
resources/js/modding-profile/posts.tsx
··· 6 6 import { BeatmapsetDiscussionMessagePostJson } from 'interfaces/beatmapset-discussion-post-json'; 7 7 import UserJson from 'interfaces/user-json'; 8 8 import { route } from 'laroute'; 9 - import { deletedUser } from 'models/user'; 9 + import { deletedUserJson } from 'models/user'; 10 10 import * as React from 'react'; 11 11 import { makeUrl } from 'utils/beatmapset-discussion-helper'; 12 12 import { classWithModifiers } from 'utils/css'; ··· 84 84 readonly 85 85 resolvedSystemPostId={-1} // TODO: Can probably move to context after refactoring state? 86 86 type='reply' 87 - user={this.props.users[post.user_id] ?? deletedUser.toJson()} 87 + user={this.props.users[post.user_id] ?? deletedUserJson} 88 88 users={this.props.users} 89 89 /> 90 90 </div>
-23
resources/js/models/legacy-pm-notification.ts
··· 1 - // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 - // See the LICENCE file in the repository root for full licence text. 3 - 4 - import Notification from 'models/notification'; 5 - import { newEmptyNotificationDetails } from 'models/notification-details'; 6 - import core from 'osu-core-singleton'; 7 - 8 - export default class LegacyPmNotification extends Notification { 9 - details = newEmptyNotificationDetails(); 10 - declare isRead: false; 11 - name = 'legacy_pm'; 12 - objectId = -1; 13 - 14 - get count() { 15 - return core.currentUser?.unread_pm_count ?? 0; 16 - } 17 - 18 - constructor() { 19 - super(-1, null); 20 - 21 - this.isRead = false; 22 - } 23 - }
+3
resources/js/models/user.ts
··· 86 86 deletedUser.isDeleted = true; 87 87 deletedUser.username = trans('users.deleted'); 88 88 89 + const deletedUserJson = deletedUser.toJson(); 90 + 89 91 export { 90 92 deletedUser, 93 + deletedUserJson, 91 94 };
-1
resources/js/notification-maps/category.ts
··· 42 42 comment_new: 'comment', 43 43 comment_reply: 'comment', 44 44 forum_topic_reply: 'forum_topic_reply', 45 - legacy_pm: 'legacy_pm', 46 45 user_achievement_unlock: 'user_achievement_unlock', 47 46 user_beatmapset_new: 'user_beatmapset_new', 48 47 user_beatmapset_revive: 'user_beatmapset_new',
-3
resources/js/notification-maps/icons.ts
··· 14 14 channel: ['fas fa-comments'], 15 15 comment: ['fas fa-comment'], 16 16 forum_topic_reply: ['fas fa-comment-medical'], 17 - legacy_pm: ['fas fa-envelope'], 18 17 user_achievement_unlock: ['fas fa-medal'], 19 18 user_beatmapset_new: ['fas fa-music'], 20 19 }; ··· 37 36 comment_new: ['fas fa-comment'], 38 37 comment_reply: ['fas fa-reply'], 39 38 forum_topic_reply: ['fas fa-comment-medical'], 40 - legacy_pm: ['fas fa-envelope'], 41 39 user_achievement_unlock: ['fas fa-trophy'], 42 40 user_beatmapset_new: ['fas fa-music'], 43 41 user_beatmapset_revive: ['fas fa-trash-restore'], ··· 61 59 comment_new: ['fas fa-comment'], 62 60 comment_reply: ['fas fa-reply'], 63 61 forum_topic_reply: ['fas fa-comment-medical'], 64 - legacy_pm: ['fas fa-envelope'], 65 62 user_beatmapset_new: ['fas fa-music'], 66 63 user_beatmapset_revive: ['fas fa-trash-restore'], 67 64 };
-4
resources/js/notification-maps/type.ts
··· 5 5 6 6 // FIXME: this mapping is not used anymore as it has been replaced by "filters"/objectType/NotificationType 7 7 export function displayType(item: Notification) { 8 - if (item.name === 'legacy_pm') { 9 - return 'legacy_pm'; 10 - } 11 - 12 8 if (item.objectType == null || item.objectId == null) { 13 9 return; 14 10 }
-8
resources/js/notification-widget/main.tsx
··· 7 7 import { observer } from 'mobx-react'; 8 8 import { Name, typeNames } from 'models/notification-type'; 9 9 import { NotificationContext } from 'notifications-context'; 10 - import LegacyPm from 'notifications/legacy-pm'; 11 10 import NotificationController from 'notifications/notification-controller'; 12 11 import NotificationReadButton from 'notifications/notification-read-button'; 13 12 import core from 'osu-core-singleton'; ··· 78 77 {this.renderMarkAsReadButton()} 79 78 </div> 80 79 </div> 81 - {this.renderLegacyPm()} 82 80 <div className='notification-stacks'> 83 81 {this.renderStacks()} 84 82 {this.renderShowMore()} ··· 142 140 {trans(`notifications.see_${this.props.only ?? 'all'}`)} 143 141 </a> 144 142 ); 145 - } 146 - 147 - private renderLegacyPm() { 148 - if (this.controller.currentFilter != null) return; 149 - 150 - return <LegacyPm />; 151 143 } 152 144 153 145 private renderMarkAsReadButton() {
-9
resources/js/notifications-index/main.tsx
··· 10 10 import { Name as NotificationTypeName, typeNames } from 'models/notification-type'; 11 11 import Stack from 'notification-widget/stack'; 12 12 import { NotificationContext, NotificationContextData } from 'notifications-context'; 13 - import LegacyPm from 'notifications/legacy-pm'; 14 13 import NotificationController from 'notifications/notification-controller'; 15 14 import NotificationDeleteButton from 'notifications/notification-delete-button'; 16 15 import NotificationReadButton from 'notifications/notification-read-button'; ··· 65 64 </div> 66 65 } 67 66 68 - {this.renderLegacyPm()} 69 - 70 67 {this.type.isEmpty 71 68 ? this.type.isLoading 72 69 ? null ··· 79 76 </div> 80 77 </div> 81 78 ); 82 - } 83 - 84 - renderLegacyPm() { 85 - if (this.controller.currentFilter != null) return; 86 - 87 - return <LegacyPm />; 88 79 } 89 80 90 81 renderShowMore() {
-30
resources/js/notifications/legacy-pm.tsx
··· 1 - // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 - // See the LICENCE file in the repository root for full licence text. 3 - 4 - import { observer } from 'mobx-react'; 5 - import LegacyPmNotification from 'models/legacy-pm-notification'; 6 - import { nameToIcons } from 'notification-maps/icons'; 7 - import Item from 'notification-widget/item'; 8 - import * as React from 'react'; 9 - import { transChoice } from 'utils/lang'; 10 - 11 - @observer 12 - export default class LegacyPm extends React.Component { 13 - render() { 14 - const item = new LegacyPmNotification(); 15 - 16 - if (item.count === 0) return null; 17 - 18 - return ( 19 - <Item 20 - icons={nameToIcons.legacy_pm} 21 - item={item} 22 - message={transChoice('notifications.item.legacy_pm.legacy_pm.legacy_pm', item.count)} 23 - modifiers={['one']} 24 - url='/forum/ucp.php?i=pm&folder=inbox' 25 - withCategory 26 - withCoverImage 27 - /> 28 - ); 29 - } 30 - }
+14 -9
resources/js/profile-page/badges.tsx
··· 1 1 // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 2 // See the LICENCE file in the repository root for full licence text. 3 3 4 + import Img2x from 'components/img2x'; 4 5 import UserBadgeJson from 'interfaces/user-badge-json'; 5 6 import * as React from 'react'; 6 - import { urlPresence } from 'utils/css'; 7 7 import { present } from 'utils/string'; 8 8 9 9 interface Props { ··· 19 19 return ( 20 20 <div className='profile-badges'> 21 21 {this.props.badges.map((badge) => { 22 - const props = { 23 - className: 'profile-badges__badge', 24 - key: badge.image_url, 25 - style: { backgroundImage: urlPresence(badge.image_url) }, 26 - title: badge.description, 27 - }; 22 + const img = ( 23 + <Img2x 24 + className='profile-badges__badge' 25 + src={badge.image_url} 26 + title={badge.description} 27 + /> 28 + ); 28 29 29 30 return present(badge.url) ? ( 30 - <a href={badge.url} {...props} /> 31 + <a key={badge.image_url} href={badge.url}> 32 + {img} 33 + </a> 31 34 ) : ( 32 - <span {...props} /> 35 + <span key={badge.image_url}> 36 + {img} 37 + </span> 33 38 ); 34 39 })} 35 40 </div>
+6 -8
resources/js/profile-page/beatmapsets.tsx
··· 88 88 </div> 89 89 ))} 90 90 91 - <div className='osu-layout__col'> 92 - <ShowMoreLink 93 - {...state.pagination} 94 - callback={this.onShowMore} 95 - data={section.urlType} 96 - modifiers='profile-page' 97 - /> 98 - </div> 91 + <ShowMoreLink 92 + {...state.pagination} 93 + callback={this.onShowMore} 94 + data={section.urlType} 95 + modifiers='profile-page' 96 + /> 99 97 </div> 100 98 )} 101 99 </React.Fragment>
+6 -3
resources/js/profile-page/controller.tsx
··· 15 15 import UserMonthlyPlaycountJson from 'interfaces/user-monthly-playcount-json'; 16 16 import UserReplaysWatchedCountJson from 'interfaces/user-replays-watched-count-json'; 17 17 import { route } from 'laroute'; 18 - import { debounce, keyBy, pullAt } from 'lodash'; 18 + import { debounce, pullAt } from 'lodash'; 19 19 import { action, makeObservable, observable, runInAction } from 'mobx'; 20 20 import core from 'osu-core-singleton'; 21 21 import { error, onErrorWithCallback } from 'utils/ajax'; ··· 94 94 } 95 95 96 96 export default class Controller { 97 - readonly achievements: Partial<Record<string, AchievementJson>>; 97 + readonly achievements: Map<number, AchievementJson>; 98 98 readonly currentMode: GameMode; 99 99 @observable currentPage: Page = 'main'; 100 100 readonly debouncedSetDisplayCoverUrl = debounce((url: string | null) => this.setDisplayCoverUrl(url), 300); ··· 130 130 this.state = JSON.parse(savedStateJson) as State; 131 131 } 132 132 133 - this.achievements = keyBy(initialData.achievements, 'id'); 133 + this.achievements = new Map(); 134 + for (const achievement of initialData.achievements) { 135 + this.achievements.set(achievement.id, achievement); 136 + } 134 137 this.currentMode = initialData.current_mode; 135 138 this.scoresNotice = initialData.scores_notice; 136 139 this.displayCoverUrl = this.state.user.cover.url;
+2 -2
resources/js/profile-page/historical.tsx
··· 132 132 /> 133 133 134 134 {this.data.beatmap_playcounts.count > 0 && 135 - <> 135 + <div> 136 136 {this.data.beatmap_playcounts.items.map((playcount) => ( 137 137 <BeatmapPlaycount 138 138 key={playcount.beatmap_id} ··· 146 146 data={'beatmapPlaycounts' as const} 147 147 modifiers='profile-page' 148 148 /> 149 - </> 149 + </div> 150 150 } 151 151 152 152 <PlayDetailList controller={this.props.controller} section='scoresRecent' />
-3
resources/js/profile-page/main.tsx
··· 13 13 import { classWithModifiers } from 'utils/css'; 14 14 import { bottomPage } from 'utils/html'; 15 15 import { hideLoadingOverlay, showLoadingOverlay } from 'utils/loading-overlay'; 16 - import { pageChange } from 'utils/page-change'; 17 16 import { nextVal } from 'utils/seq'; 18 17 import { present } from 'utils/string'; 19 18 import { switchNever } from 'utils/switch-never'; ··· 152 151 update: this.updateOrder, 153 152 }); 154 153 } 155 - 156 - pageChange(); 157 154 158 155 // preserve scroll if existing saved state but force position to reset 159 156 // on refresh to avoid browser setting scroll position at the bottom on reload.
+2 -4
resources/js/profile-page/medals.tsx
··· 28 28 // group by .grouping and then further group by .ordering 29 29 const ret = new Map<string, Map<number, UserAchievementData[]>>(); 30 30 31 - for (const achievement of Object.values(this.props.controller.achievements)) { 32 - if (achievement == null) continue; 33 - 31 + for (const achievement of [...this.props.controller.achievements.values()]) { 34 32 const userAchievement = this.userAchievements[achievement.id.toString()]; 35 33 const visible = this.currentModeFilter(achievement) && (isCurrentUser || userAchievement != null); 36 34 ··· 58 56 const ret: Required<UserAchievementData>[] = []; 59 57 60 58 for (const ua of this.props.controller.state.user.user_achievements) { 61 - const achievement = this.props.controller.achievements[ua.achievement_id]; 59 + const achievement = this.props.controller.achievements.get(ua.achievement_id); 62 60 63 61 if (achievement != null && this.currentModeFilter(achievement)) { 64 62 ret.push({
+10 -10
resources/js/profile-page/play-detail-list.tsx
··· 122 122 titleKey={`users.show.extra.${this.sectionMap.translationKey}.title`} 123 123 /> 124 124 125 - <ContainerContext.Provider value={this.containerContextValue}> 126 - <div ref={this.listRef} className={`${classWithModifiers('play-detail-list', { 'menu-active': this.activeKey != null })} u-relative`}> 125 + <div ref={this.listRef} className={`${classWithModifiers('play-detail-list', { 'menu-active': this.activeKey != null })} u-relative`}> 126 + <ContainerContext.Provider value={this.containerContextValue}> 127 127 {(this.uniqueItems).map((score) => ( 128 128 <KeyContext.Provider key={score.id} value={score.id}> 129 129 <PlayDetail ··· 135 135 /> 136 136 </KeyContext.Provider> 137 137 ))} 138 - </div> 139 - </ContainerContext.Provider> 138 + </ContainerContext.Provider> 140 139 141 - <ShowMoreLink 142 - {...this.scores.pagination} 143 - callback={this.onShowMore} 144 - data={this.props.section} 145 - modifiers='profile-page' 146 - /> 140 + <ShowMoreLink 141 + {...this.scores.pagination} 142 + callback={this.onShowMore} 143 + data={this.props.section} 144 + modifiers='profile-page' 145 + /> 146 + </div> 147 147 </> 148 148 ); 149 149 }
+1 -1
resources/js/profile-page/recent-activity.tsx
··· 66 66 return ( 67 67 <ul className='profile-extra-entries'> 68 68 {this.data.items.map(this.renderEntry)} 69 - <li className='profile-extra-entries__item'> 69 + <li className='profile-extra-entries__item u-contents'> 70 70 <ShowMoreLink 71 71 {...this.data.pagination} 72 72 callback={this.onShowMore}
+2 -2
resources/js/register-components.tsx
··· 21 21 import { WikiSearch } from 'components/wiki-search'; 22 22 import { keyBy } from 'lodash'; 23 23 import { observable } from 'mobx'; 24 - import { deletedUser } from 'models/user'; 24 + import { deletedUserJson } from 'models/user'; 25 25 import NotificationWidget from 'notification-widget/main'; 26 26 import core from 'osu-core-singleton'; 27 27 import QuickSearch from 'quick-search/main'; ··· 59 59 60 60 // TODO: move to store? 61 61 // eslint-disable-next-line id-blacklist 62 - props.users.null = props.users.undefined = deletedUser.toJson(); 62 + props.users.null = props.users.undefined = deletedUserJson; 63 63 64 64 return <BeatmapsetEvents {...props} />; 65 65 });
+2 -2
resources/js/socket-worker.ts
··· 145 145 return json; 146 146 } 147 147 148 - console.debug('message missing event type.'); 148 + console.error('message missing event type.'); 149 149 } catch { 150 - console.debug('Failed parsing data:', event.data); 150 + console.error('Failed parsing data:', event.data); 151 151 } 152 152 } 153 153
+1 -3
resources/js/spoilerbox.coffee
··· 1 1 # Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 2 # See the LICENCE file in the repository root for full licence text. 3 3 4 - import { pageChange } from 'utils/page-change' 5 - 6 4 $(document).on 'click', '.js-spoilerbox__link', (e) -> 7 5 e.preventDefault() 8 6 9 7 $link = $(e.target).closest('.js-spoilerbox') 10 8 11 9 $link.toggleClass 'js-spoilerbox--open' 12 - pageChange() 10 + $.publish 'sync-height:force'
+2 -2
resources/js/stores/channel-store.ts
··· 243 243 const message = event.message; 244 244 const channel = this.get(message.channelId); 245 245 if (channel == null) { 246 - console.debug('channel missing'); 246 + console.error('channel missing'); 247 247 return; 248 248 } 249 249 ··· 254 254 const userId = channel.pmTarget; 255 255 256 256 if (userId == null) { 257 - console.debug('sendMessage:: userId not found?? this shouldn\'t happen'); 257 + console.error('sendMessage:: userId not found?? this shouldn\'t happen'); 258 258 return; 259 259 } 260 260
-2
resources/js/stores/notification-stack-store.ts
··· 7 7 import DispatchListener from 'dispatch-listener'; 8 8 import NotificationJson, { NotificationBundleJson, NotificationStackJson, NotificationTypeJson } from 'interfaces/notification-json'; 9 9 import { action, computed, makeObservable, observable } from 'mobx'; 10 - import LegacyPmNotification from 'models/legacy-pm-notification'; 11 10 import Notification from 'models/notification'; 12 11 import NotificationStack, { idFromJson } from 'models/notification-stack'; 13 12 import NotificationType, { Name as NotificationTypeName } from 'models/notification-type'; ··· 19 18 20 19 @dispatchListener 21 20 export default class NotificationStackStore implements DispatchListener { 22 - @observable readonly legacyPm = new LegacyPmNotification(); 23 21 @observable readonly types = new Map<string | null, NotificationType>(); 24 22 private deletedStacks = new Set<string>(); 25 23 private readonly resolver = new NotificationResolver();
-10
resources/js/utils/page-change.ts
··· 1 - // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 2 - // See the LICENCE file in the repository root for full licence text. 3 - 4 - export function pageChange() { 5 - return window.setTimeout(pageChangeImmediate, 0); 6 - } 7 - 8 - export function pageChangeImmediate() { 9 - $.publish('osu:page:change'); 10 - }
+1
resources/lang/ar/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'يمكن لمالك النتيجة فقط تثبيتها.', 175 176 'too_many' => 'قمت بتثبيت نتائج كثيرة.', 176 177 ],
-9
resources/lang/ar/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'نظام الرسائل القديم', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited رسالة غير مقروءة|:count_delimited رسائل غير مقروءة', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'خريطة جديدة',
+7
resources/lang/ar/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'منطقة ألأضواء', 22 28 'country' => 'الدولة', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'متعدد اللاعبين', 24 31 'performance' => 'الأداء', 25 32 'score' => 'النقاط',
+1
resources/lang/be/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Толькі ўладальнік можа замацаваць скор.', 175 176 'too_many' => 'Замацавана вельмі шмат скораў.', 176 177 ],
-9
resources/lang/be/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Правілы Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited непрачытанае паведамленне.|:count_delimited ннепрачытанныя паведамленні.', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Новая бітмапа',
+7
resources/lang/be/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'па чартам', 22 28 'country' => 'па краінам', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'мультыплэер', 24 31 'performance' => 'па прадукцыйнасці', 25 32 'score' => 'па ачках',
+1
resources/lang/bg/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Само притежателят на резултата може да го закачи.', 175 176 'too_many' => 'Закачени са прекалено много резултати.', 176 177 ],
-9
resources/lang/bg/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Стар форум за ЛС', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited непрочетено съобщение|:count_delimited непрочетени съобщения', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Нов бийтмап',
+7
resources/lang/bg/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'под прожекторите', 22 28 'country' => 'държава', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'мултиплейър', 24 31 'performance' => 'представяне', 25 32 'score' => 'резултат',
+1
resources/lang/ca/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Només el propietari de la puntuació pot fixar la puntuació.', 175 176 'too_many' => 'Has fixat massa puntuacions.', 176 177 ],
-9
resources/lang/ca/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'MP del fòrum antic', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited missatge no llegit|:count_delimited missatges no llegits', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nou beatmap',
+7
resources/lang/ca/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'focus', 22 28 'country' => 'país', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multijugador', 24 31 'performance' => 'rendiment', 25 32 'score' => 'puntuació',
+2 -2
resources/lang/cs/artist.php
··· 13 13 14 14 'beatmaps' => [ 15 15 '_' => 'Beatmapy', 16 - 'download' => 'Stáhnout šablonu beatmapy', 17 - 'download-na' => 'Šablona beatmapy zatím není dostupná', 16 + 'download' => 'stáhnout šablonu beatmapy', 17 + 'download-na' => 'šablona beatmapy zatím není dostupná', 18 18 ], 19 19 20 20 'index' => [
+1
resources/lang/cs/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Pouze vlastník skóre může připnout skóre.', 175 176 'too_many' => 'Připnuto příliš mnoho skóre.', 176 177 ],
+3 -3
resources/lang/cs/beatmaps.php
··· 106 106 'unsaved' => 'Neuloženo', 107 107 'timestamp' => [ 108 108 'all-diff' => 'Příspěvky na "Všechny obtížnosti" nemohou být časovány.', 109 - 'diff' => 'Pokud tento :type začíná časovou značkou, zobrazí se v Časové ose.', 109 + 'diff' => 'Pokud tento příspěvek začíná časovou značkou, zobrazí se v Časové ose.', 110 110 ], 111 111 ], 112 112 'insert-block' => [ ··· 176 176 177 177 'nominations' => [ 178 178 'already_nominated' => 'Už jsi tuto beatmapu nominoval.', 179 - 'cannot_nominate' => '', 179 + 'cannot_nominate' => 'Nemůžeš nominovat tento herní mód beatmapy.', 180 180 'delete' => 'Vymazat', 181 181 'delete_own_confirm' => 'Jste si jistý? Tahle beatmapa bude smazána a pošleme vás zpátky na váš profil.', 182 182 'delete_other_confirm' => 'Jste si jistý? Tahle beatmapa bude smazána a pošleme vás zpátky na profil uživatele.', ··· 251 251 ], 252 252 'supporter_filter_quote' => [ 253 253 '_' => 'Filtrování podle :filters vyžaduje aktivní :link', 254 - 'link_text' => 'stítek podporovatele', 254 + 'link_text' => 'osu!supporter tag', 255 255 ], 256 256 ], 257 257 ],
+4 -4
resources/lang/cs/beatmapsets.php
··· 67 67 68 68 'details' => [ 69 69 'by_artist' => 'od :artist', 70 - 'favourite' => 'Přidat do mých oblíbených', 71 - 'favourite_login' => 'Pro přidání beatmapy do oblíbených se přihlas', 72 - 'logged-out' => 'Pro stahování beatmap musíš být přihlášen!', 70 + 'favourite' => 'přidat do mých oblíbených', 71 + 'favourite_login' => 'pro přidání beatmapy do oblíbených se přihlas', 72 + 'logged-out' => 'před stahováním beatmap se musíš nejprve přihlásit!', 73 73 'mapped_by' => 'beatmapu vytvořil :mapper', 74 74 'mapped_by_guest' => 'obtížnost hosta od :mapper', 75 - 'unfavourite' => 'Odebrat z mých oblíbených', 75 + 'unfavourite' => 'odebrat z mých oblíbených', 76 76 'updated_timeago' => 'naposledy aktualizováno :timeago', 77 77 78 78 'download' => [
+1 -1
resources/lang/cs/comments.php
··· 11 11 'edited' => 'upraveno před :timeago uživatelem :user', 12 12 'pinned' => 'připnuto', 13 13 'empty' => 'Zatím zde nejsou žádné komentáře.', 14 - 'empty_other' => '', 14 + 'empty_other' => 'Zatím zde nejsou žádné další komentáře.', 15 15 'load_replies' => 'načíst odpovědi', 16 16 'replies_count' => ':count_delimited odpověď|:count_delimited odpovědi|:count_delimited odpovědí', 17 17 'title' => 'Komentáře',
+1 -1
resources/lang/cs/events.php
··· 15 15 'rank' => '<strong><em>:user</em></strong> získal pozici #:rank na mapě <em>:beatmap</em> (:mode)', 16 16 'rank_lost' => '<strong><em>:user</em></strong> ztratil první místo na mapě <em>:beatmap</em> (:mode)', 17 17 'user_support_again' => '<strong>:user</strong> se opět rozhodl podpořit osu! - díky za tvou štědrost!', 18 - 'user_support_first' => '<strong>:user</strong> se stal osu! supporterem - díky za tvou štědrost!', 18 + 'user_support_first' => '<strong>:user</strong> podpořil osu! - díky za tvou štědrost!', 19 19 'user_support_gift' => '<strong>:user</strong> obdržel dar osu! supporteru!', 20 20 'username_change' => '<strong>:previousUsername</strong> se přejmenoval na <strong><em>:user</strong></em>!', 21 21
+1 -1
resources/lang/cs/forum.php
··· 102 102 'preview' => 'Náhled', 103 103 // TL note: this is used in the topic reply preview, when 104 104 // the user goes back from previewing to editing the reply 105 - 'preview_hide' => 'Psát', 105 + 'preview_hide' => 'Editovat', 106 106 'submit' => 'Odeslat', 107 107 108 108 'necropost' => [
+1 -1
resources/lang/cs/model_validation.php
··· 122 122 'oauth' => [ 123 123 'client' => [ 124 124 'too_many' => 'Byl překročen limit povolených možností.', 125 - 'url' => 'Zadejte prosím platnou adresu URL.', 125 + 'url' => 'Zadejte prosím platné adresy URL.', 126 126 127 127 'attributes' => [ 128 128 'name' => 'Název aplikace',
-9
resources/lang/cs/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'SZ původního fóra', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited nepřečtená zpráva|:count_delimited nepřečtené zprávy|:count_delimited nepřečtených zpráv', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nová beatmapa',
+1 -1
resources/lang/cs/oauth.php
··· 27 27 'client' => [ 28 28 'id' => 'ID klienta', 29 29 'name' => 'Název aplikace', 30 - 'redirect' => 'URL zpětného volání aplikace', 30 + 'redirect' => 'URL adresy zpětného volání aplikace', 31 31 'reset' => 'Resetovat tajný klíč klienta', 32 32 'reset_failed' => 'Obnovení tajného klíče klienta se nezdařilo', 33 33 'secret' => 'Tajný klíč klienta',
+7
resources/lang/cs/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'výběry', 22 28 'country' => 'stát', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'hra pro více hráčů', 24 31 'performance' => 'výkon', 25 32 'score' => 'skóre',
+1 -1
resources/lang/cs/tournament.php
··· 13 13 ], 14 14 15 15 'item' => [ 16 - 'registered' => 'Registrovaní hráči', 16 + 'registered' => 'registrovaní hráči', 17 17 ], 18 18 19 19 'state' => [
+4 -4
resources/lang/cs/users.php
··· 49 49 ], 50 50 51 51 'card' => [ 52 - 'gift_supporter' => '', 52 + 'gift_supporter' => 'Darovat supporter tag', 53 53 'loading' => 'Načítání...', 54 54 'send_message' => 'Odeslat zprávu', 55 55 ], ··· 159 159 ], 160 160 'restricted_banner' => [ 161 161 'title' => 'Tvůj účet byl omezen!', 162 - 'message' => 'Zatímco jsi omezený, nebudeš moci komunikovat s ostatními hráči a tvá skóre budou viditelná pouze pro tebe. Toto je obvykle výsledkem automatického procesu, který by se měl sám vyřešit nejpozději do 24 hodin. Pokud si přeješ odvolat své omezení, prosím <a href="mailto:accounts@ppy.sh">kontaktuj podporu</a>.', 162 + 'message' => 'Zatímco jsi omezený, nebudeš moci komunikovat s ostatními hráči a tvá skóre budou viditelná pouze pro tebe. Toto je obvykle výsledkem automatického procesu a většinou jsou tato omezení zrušena do 24 hodin. :link', 163 163 'message_link' => 'Na této stránce se dozvíte více.', 164 164 ], 165 165 'show' => [ ··· 417 417 'title' => 'Uživatel nebyl nalezen! ;_;', 418 418 ], 419 419 'page' => [ 420 - 'button' => 'Upravit stránku profilu', 420 + 'button' => 'upravit stránku profilu', 421 421 'description' => '<strong>já!</strong> je osobní přizpůsobitelná plocha na vašem profilu.', 422 422 'edit_big' => 'Uprav mě!', 423 423 'placeholder' => 'Zde napiš obsah stánky', ··· 441 441 'stats' => [ 442 442 'hit_accuracy' => 'Přesnost zásahů', 443 443 'level' => 'Úroveň :level', 444 - 'level_progress' => 'Postup do dalšího levelu', 444 + 'level_progress' => 'postup do dalšího levelu', 445 445 'maximum_combo' => 'Maximální Combo', 446 446 'medals' => 'Medaile', 447 447 'play_count' => 'Počet zahrání',
+1
resources/lang/da/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Kun score ejer kan pin score.', 175 176 'too_many' => 'Fastgjort for mange score.', 176 177 ],
-9
resources/lang/da/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Legacy Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited ulæst besked|:count_delimited ulæste beskeder', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nyt beatmap',
+7
resources/lang/da/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Baner', 22 28 'country' => 'Land', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multiplayer', 24 31 'performance' => 'Præstation', 25 32 'score' => 'Score',
+1
resources/lang/de/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Nur der Spieler, der den Score eingereicht hat, kann ihn anpinnen.', 175 176 'too_many' => 'Zu viele Scores angepinnt.', 176 177 ],
+1 -1
resources/lang/de/beatmappacks.php
··· 27 27 'not_cleared' => 'nicht geschafft', 28 28 ], 29 29 'no_diff_reduction' => [ 30 - '_' => ':link darf zum Absolvieren dieses Beatmap-Packs nicht verwendet werden.', 30 + '_' => ':link dürfen zum Absolvieren dieses Beatmap-Pakets nicht verwendet werden.', 31 31 'link' => 'Mods zur Vereinfachung der Schwierigkeit', 32 32 ], 33 33 ],
-9
resources/lang/de/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Alt-Forum PN', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited ungelesene Nachricht|:count_delimited ungelesene Nachrichten', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Neue Beatmap',
+7
resources/lang/de/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Spotlights', 22 28 'country' => 'Länder', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'Mehrspieler', 24 31 'performance' => 'Performance', 25 32 'score' => 'Punktzahl',
+1
resources/lang/el/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '', 175 176 'too_many' => '', 176 177 ],
-9
resources/lang/el/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Προσωπικά Μηνύματα του Παλαιότερου Forum', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited αδιάβαστο μήνυμα.|:count_delimited αδιάβαστα μηνύματα.', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '',
+7
resources/lang/el/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Spotlights', 22 28 'country' => 'Χώρας', 29 + 'kudosu' => '', 23 30 'multiplayer' => '', 24 31 'performance' => 'Επίδοσης', 25 32 'score' => 'Σκορ',
+6
resources/lang/en/accounts.php
··· 34 34 ], 35 35 36 36 'profile' => [ 37 + 'country' => 'country', 37 38 'title' => 'Profile', 39 + 40 + 'country_change' => [ 41 + '_' => "It looks like your account country doesn't match your country of residence. :update_link.", 42 + 'update_link' => 'Update to :country', 43 + ], 38 44 39 45 'user' => [ 40 46 'user_discord' => 'discord',
+3 -3
resources/lang/en/artist.php
··· 4 4 // See the LICENCE file in the repository root for full licence text. 5 5 6 6 return [ 7 - 'page_description' => 'Featured artists on osu!', 7 + 'page_description' => 'Featured Artists on osu!', 8 8 'title' => 'Featured Artists', 9 9 10 10 'admin' => [ ··· 18 18 ], 19 19 20 20 'index' => [ 21 - 'description' => 'Featured artists are artists that we are working in collaboration with in order to bring new and original music to osu!. These artists and a selection of their tracks have been hand-picked by the osu! team as being awesomesauce and suitable for mapping. Some of these featured artists have also created exclusive new tracks for use in osu!.<br><br>All tracks in this section are provided as pre-timed .osz files and have been officially licensed for use in osu! and osu!-related content.', 21 + 'description' => 'Featured Artists are artists that we are working in collaboration with in order to bring new and original music to osu!. These artists and a selection of their tracks have been hand-picked by the osu! team as being awesomesauce and suitable for mapping. Some of these Featured Artists have also created exclusive new tracks for use in osu!.<br><br>All tracks in this section are provided as pre-timed .osz files and have been officially licensed for use in osu! and osu!-related content.', 22 22 ], 23 23 24 24 'links' => [ ··· 43 43 44 44 'tracks' => [ 45 45 'index' => [ 46 - '_' => 'tracks search', 46 + '_' => 'track search', 47 47 48 48 'form' => [ 49 49 'advanced' => 'Advanced Search',
+1 -1
resources/lang/en/beatmaps.php
··· 257 257 ], 258 258 'general' => [ 259 259 'converts' => 'Include converted beatmaps', 260 - 'featured_artists' => 'Featured artists', 260 + 'featured_artists' => 'Featured Artists', 261 261 'follows' => 'Subscribed mappers', 262 262 'recommended' => 'Recommended difficulty', 263 263 'spotlights' => 'Spotlighted beatmaps',
+1 -1
resources/lang/en/beatmapsets.php
··· 20 20 ], 21 21 22 22 'featured_artist_badge' => [ 23 - 'label' => 'Featured artist', 23 + 'label' => 'Featured Artist', 24 24 ], 25 25 26 26 'index' => [
-9
resources/lang/en/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Legacy Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited unread message|:count_delimited unread messages', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'New beatmap',
+1
resources/lang/es/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Solo el propietario puede anclar la puntuación.', 175 176 'too_many' => 'Se han anclado demasiadas puntuaciones.', 176 177 ],
-9
resources/lang/es/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'MP del foro antiguo', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited mensaje sin leer|:count_delimited mensajes sin leer', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nuevo mapa',
+7
resources/lang/es/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'destacados', 22 28 'country' => 'país', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multijugador', 24 31 'performance' => 'rendimiento', 25 32 'score' => 'puntuación',
+1
resources/lang/fa-IR/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'فقط صاحب امتیاز می تواند آن را سنجاق کند.', 175 176 'too_many' => 'تعداد زیادی امتیاز سنجاق شده است.', 176 177 ],
-9
resources/lang/fa-IR/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => '', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '',
+7
resources/lang/fa-IR/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => '', 22 28 'country' => '', 29 + 'kudosu' => '', 23 30 'multiplayer' => '', 24 31 'performance' => '', 25 32 'score' => '',
+1
resources/lang/fi/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Vain tuloksen omistaja voi kiinnittää tuloksen.', 175 176 'too_many' => 'Kiinnitit liian monta tulosta.', 176 177 ],
-9
resources/lang/fi/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited lukematon viesti.|:count_delimited lukemattomia viestejä.', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Uusi beatmappi',
+7
resources/lang/fi/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Valokeilassa', 22 28 'country' => 'Maa', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'moninpeli', 24 31 'performance' => 'Suorituskyky', 25 32 'score' => 'Piste',
+1
resources/lang/fil/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Tanging ang may-ari ng iskor ang maaaring mag-pin ng iskor.', 175 176 'too_many' => 'Nag-pin ng masyadong maraming mga iskor.', 176 177 ],
-9
resources/lang/fil/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Lumang Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited na hindi pa nabasang mensahe|:count_delimited na hindi pa nabasang mga mensahe', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Bagong beatmap',
+7
resources/lang/fil/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Mga Spotlight', 22 28 'country' => 'Bansa', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multiplayer', 24 31 'performance' => 'Performance', 25 32 'score' => 'Iskor',
+1
resources/lang/fr/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Seul le propriétaire du score peut épingler le score.', 175 176 'too_many' => 'Trop de scores épinglés.', 176 177 ],
-9
resources/lang/fr/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Ancienne page forum des messages privés', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited message non lu|:count_delimited messages non lus', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nouvelle beatmap',
+7
resources/lang/fr/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'spotlights', 22 28 'country' => 'pays', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multijoueur', 24 31 'performance' => 'performance', 25 32 'score' => 'score',
+1
resources/lang/he/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '', 175 176 'too_many' => '', 176 177 ],
-9
resources/lang/he/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'הודעה פרטית ישנה', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited הודעה שלא נקראה.|:count_delimited הודעות שלא נקראו.', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'מפה חדשה',
+7
resources/lang/he/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'זרקורים', 22 28 'country' => 'מדינה', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'רב משתתפים', 24 31 'performance' => 'ביצועים', 25 32 'score' => 'תוצאה',
+1
resources/lang/hr-HR/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Samo vlasnik rezultata može prikvačiti rezultat.', 175 176 'too_many' => 'Prikvačeno previše rezultata.', 176 177 ],
-9
resources/lang/hr-HR/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Legacy Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited nepročitana poruka|:count_delimited nepročitane poruke', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nova beatmapa',
+7
resources/lang/hr-HR/rankings.php
··· 19 19 ], 20 20 ], 21 21 22 + 'kudosu' => [ 23 + 'total' => '', 24 + 'available' => '', 25 + 'used' => '', 26 + ], 27 + 22 28 'type' => [ 23 29 'charts' => 'istaknuto', 24 30 'country' => 'države', 31 + 'kudosu' => '', 25 32 'multiplayer' => 'multiplayer', 26 33 'performance' => 'izvedba', 27 34 'score' => 'bodovi',
+1
resources/lang/hu/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Csak eredménnyel rendelkezők tűzhetnek ki eredményeket.', 175 176 'too_many' => 'Túl sok kitűzött eredmény.', 176 177 ],
-9
resources/lang/hu/notifications.php
··· 154 154 ], 155 155 ], 156 156 157 - 'legacy_pm' => [ 158 - '_' => 'Hivatalos PM fórum', 159 - 160 - 'legacy_pm' => [ 161 - '_' => '', 162 - 'legacy_pm' => ':count_delimited olvasatlan üzenet.|:count_delimited olvasatlan üzenet.', 163 - ], 164 - ], 165 - 166 157 'user' => [ 167 158 'user_beatmapset_new' => [ 168 159 '_' => 'Új beatmap',
+7
resources/lang/hu/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Reflektorfény', 22 28 'country' => 'Ország', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'többjátékos', 24 31 'performance' => 'Teljesítmény', 25 32 'score' => 'Pontszám',
+1
resources/lang/id/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Hanya pemilik skor yang dapat menyematkan skor.', 175 176 'too_many' => 'Skor yang disematkan sudah terlalu banyak.', 176 177 ],
+1 -1
resources/lang/id/beatmaps.php
··· 163 163 'confirm' => "Apakah kamu yakin? Dengan ini, kamu akan memberikan 1 hype kepada beatmap ini dari :n hype yang kamu miliki saat ini. Tindakan ini tidak dapat diurungkan.", 164 164 'explanation' => 'Berikan hype-mu untuk membawa beatmap ini lebih dekat menuju Ranked!', 165 165 'explanation_guest' => 'Masuk dan berikan hype kepada beatmap ini agar beatmap ini dapat segera dinominasikan dan di-rank!', 166 - 'new_time' => "Anda akan mendapatkan hype tambahan :new_time.", 166 + 'new_time' => "Kamu akan memperoleh lebih banyak hype :new_time.", 167 167 'remaining' => 'Kamu memiliki :remaining hype tersisa.', 168 168 'required_text' => 'Hype: :current/:required', 169 169 'section_title' => 'Hype Train',
-9
resources/lang/id/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited pesan yang belum dibaca.|:count_delimited pesan yang belum dibaca.', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Beatmap baru',
+7
resources/lang/id/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'spotlights', 22 28 'country' => 'negara', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multiplayer', 24 31 'performance' => 'performa', 25 32 'score' => 'skor',
+1 -1
resources/lang/id/users.php
··· 329 329 'title' => 'saya!', 330 330 ], 331 331 'medals' => [ 332 - 'empty' => "Pengguna ini belum membuka medali apapun. ;_;", 332 + 'empty' => "Pengguna ini belum membuka medali apa pun. ;_;", 333 333 'recent' => 'Terbaru', 334 334 'title' => 'Medali', 335 335 ],
+1
resources/lang/it/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Solo il proprietario del punteggio può fissarlo.', 175 176 'too_many' => 'Hai già fissato troppi punteggi.', 176 177 ],
-9
resources/lang/it/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'PM forum legacy', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited messaggio non letto|:count_delimited messaggi non letti', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nuova beatmap',
+7
resources/lang/it/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'spotlight', 22 28 'country' => 'paese', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multigiocatore', 24 31 'performance' => 'performance', 25 32 'score' => 'punteggio',
+1
resources/lang/ja/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'スコアの所有者のみがピン留めできます。', 175 176 'too_many' => 'ピン留めの数が多すぎます。', 176 177 ],
+1 -1
resources/lang/ja/beatmapsets.php
··· 61 61 'discussion' => 'ディスカッション', 62 62 63 63 'deleted_banner' => [ 64 - 'title' => '', 64 + 'title' => 'このビートマップは削除されました。', 65 65 'message' => '', 66 66 ], 67 67
-9
resources/lang/ja/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'レガシーフォーラムPM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited個の未読メッセージ', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '新しいビートマップ',
+7
resources/lang/ja/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'スポットライト', 22 28 'country' => '国別', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'マルチプレイ', 24 31 'performance' => 'パフォーマンス', 25 32 'score' => 'スコア',
+1 -1
resources/lang/ja/users.php
··· 49 49 ], 50 50 51 51 'card' => [ 52 - 'gift_supporter' => '', 52 + 'gift_supporter' => 'サポータータグを贈る', 53 53 'loading' => '読み込み中・・・', 54 54 'send_message' => 'メッセージの送信', 55 55 ],
+134
resources/lang/kk-KZ/accounts.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'edit' => [ 8 + 'title_compact' => 'аккаунт параметрлері', 9 + 'username' => 'пайдаланушы аты', 10 + 11 + 'avatar' => [ 12 + 'title' => 'Аватар', 13 + 'rules' => 'Өтініш, аватарыңыз :link бойынша келуін қадағалаңыз.<br/>Ол <strong>барлық жастарға сай болуы керек</strong>, яғни жалаңаштық, бейпіл сөздер немесе ерсі контент болмауы тиіс.', 14 + 'rules_link' => 'қауымдастық ережелері', 15 + ], 16 + 17 + 'email' => [ 18 + 'new' => 'жаңа пошта', 19 + 'new_confirmation' => 'email-ды растаңыз', 20 + 'title' => 'Email', 21 + ], 22 + 23 + 'legacy_api' => [ 24 + 'api' => 'api', 25 + 'irc' => 'irc', 26 + 'title' => 'Ескірген API', 27 + ], 28 + 29 + 'password' => [ 30 + 'current' => 'қазіргі құпиясөз', 31 + 'new' => 'жаңа құпиясөз', 32 + 'new_confirmation' => 'құпиясөзді растаңыз', 33 + 'title' => 'Құпиясөз', 34 + ], 35 + 36 + 'profile' => [ 37 + 'title' => 'Профиль', 38 + 39 + 'user' => [ 40 + 'user_discord' => '', 41 + 'user_from' => 'тұрғылықты жері', 42 + 'user_interests' => 'қызығушылықтары', 43 + 'user_occ' => 'мамандығы', 44 + 'user_twitter' => '', 45 + 'user_website' => 'веб-сайт', 46 + ], 47 + ], 48 + 49 + 'signature' => [ 50 + 'title' => 'Қолы', 51 + 'update' => 'жаңарту', 52 + ], 53 + ], 54 + 55 + 'notifications' => [ 56 + 'beatmapset_discussion_qualified_problem' => 'келесі режимдердің білікті карталарындағы жаңа мәселелерге байланысты хабарландырулар алу', 57 + 'beatmapset_disqualify' => 'келесі режимдердің карталары дисквалификацияланған жағдайда хабарландырулар алу', 58 + 'comment_reply' => 'пікірлеріңіздің жауаптары туралы хабарландырулар алу', 59 + 'title' => 'Хабарландырулар', 60 + 'topic_auto_subscribe' => 'сіз құрған жаңа форум тақырыптарының хабарландыруларын автоматты түрде қосу', 61 + 62 + 'options' => [ 63 + '_' => 'алу әдістері', 64 + 'beatmap_owner_change' => 'қонақтық қиындық', 65 + 'beatmapset:modding' => 'карта модтау', 66 + 'channel_message' => 'жеке хабарламалар', 67 + 'comment_new' => 'жаңа пікірлер', 68 + 'forum_topic_reply' => 'тақырып жауабы', 69 + 'mail' => 'email', 70 + 'mapping' => 'карта маппері', 71 + 'push' => 'push', 72 + 'user_achievement_unlock' => 'жаңа медальдар', 73 + ], 74 + ], 75 + 76 + 'oauth' => [ 77 + 'authorized_clients' => 'авторландырылған клиенттер', 78 + 'own_clients' => 'өз клиенттеріңіз', 79 + 'title' => 'OAuth', 80 + ], 81 + 82 + 'options' => [ 83 + 'beatmapset_show_nsfw' => 'карталардағы ерсі контент ескертулерін жасыру', 84 + 'beatmapset_title_show_original' => 'карта метадеректерін түпнұсқа тілінде көрсету', 85 + 'title' => 'Баптаулар', 86 + 87 + 'beatmapset_download' => [ 88 + '_' => 'әдепкі карта жүктеу типі', 89 + 'all' => 'видеомен, бар болған жағдайда', 90 + 'direct' => 'osu!direct-те ашу', 91 + 'no_video' => 'видеосыз', 92 + ], 93 + ], 94 + 95 + 'playstyles' => [ 96 + 'keyboard' => 'пернетақта', 97 + 'mouse' => 'тышқан', 98 + 'tablet' => 'графикалық планшет', 99 + 'title' => 'Ойнау стильдері', 100 + 'touch' => 'сенсорлы экран', 101 + ], 102 + 103 + 'privacy' => [ 104 + 'friends_only' => 'достардан келмеген жеке хабарламаларды бұғаттау', 105 + 'hide_online' => 'желіде екеніңізді жасыру', 106 + 'title' => 'Құпиялық', 107 + ], 108 + 109 + 'security' => [ 110 + 'current_session' => 'қазіргі', 111 + 'end_session' => 'Сессияны аяқтау', 112 + 'end_session_confirmation' => 'Осы құрылғыдағы сеанс бірден аяқталады. Сіз сенімдісіз ме?', 113 + 'last_active' => 'Соңғы белсенділік:', 114 + 'title' => 'Қауіпсіздік', 115 + 'web_sessions' => 'веб-сессиялар', 116 + ], 117 + 118 + 'update_email' => [ 119 + 'update' => 'жаңарту', 120 + ], 121 + 122 + 'update_password' => [ 123 + 'update' => 'жаңарту', 124 + ], 125 + 126 + 'verification_completed' => [ 127 + 'text' => 'Енді бетбелгіні/терезені жаба аласыз', 128 + 'title' => 'Верификациялау аяқталды', 129 + ], 130 + 131 + 'verification_invalid' => [ 132 + 'title' => 'Қате немесе ескірген верификация сілтемесі', 133 + ], 134 + ];
+67
resources/lang/kk-KZ/admin.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'beatmapsets' => [ 8 + 'covers' => [ 9 + 'regenerate' => '', 10 + 'regenerating' => '', 11 + 'remove' => '', 12 + 'removing' => '', 13 + 'title' => '', 14 + ], 15 + 'show' => [ 16 + 'covers' => '', 17 + ], 18 + ], 19 + 20 + 'forum' => [ 21 + 'forum-covers' => [ 22 + 'index' => [ 23 + 'delete' => '', 24 + 25 + 'forum-name' => '', 26 + 27 + 'no-cover' => '', 28 + 29 + 'submit' => [ 30 + 'save' => '', 31 + 'update' => '', 32 + ], 33 + 34 + 'title' => '', 35 + 36 + 'type-title' => [ 37 + 'default-topic' => '', 38 + 'main' => '', 39 + ], 40 + ], 41 + ], 42 + ], 43 + 44 + 'logs' => [ 45 + 'index' => [ 46 + 'title' => '', 47 + ], 48 + ], 49 + 50 + 'pages' => [ 51 + 'root' => [ 52 + 'sections' => [ 53 + 'beatmapsets' => '', 54 + 'forum' => '', 55 + 'general' => '', 56 + ], 57 + ], 58 + ], 59 + 60 + 'users' => [ 61 + 'restricted_banner' => [ 62 + 'title' => '', 63 + 'message' => '', 64 + ], 65 + ], 66 + 67 + ];
+33
resources/lang/kk-KZ/api.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'error' => [ 8 + 'chat' => [ 9 + 'empty' => 'Бос хабарлама жібере алмайсыз.', 10 + 'limit_exceeded' => 'Сіз хабарламаларды тым жылдам жіберіп жатырсыз. Өтініш, күте тұрыңыз.', 11 + 'too_long' => 'Жібергіңіз келетін хабарлама тым ұзын.', 12 + ], 13 + ], 14 + 15 + 'scopes' => [ 16 + 'bot' => 'Чат-бот ретінде әрекет ету.', 17 + 'identify' => 'Сізді идентификациялау және сіздің көпшілікке қолжетімді деректеріңізді оқу.', 18 + 19 + 'chat' => [ 20 + 'write' => 'Сіздің атыңыздан хабарламалар жіберу.', 21 + ], 22 + 23 + 'forum' => [ 24 + 'write' => 'Сіздің атыңыздан форум тақырыптарын және посттарын құрау және редакциялау.', 25 + ], 26 + 27 + 'friends' => [ 28 + 'read' => 'Кімдерге жазылғаныңызды көру.', 29 + ], 30 + 31 + 'public' => 'Сіздің атыңыздан жария деректерді оқу.', 32 + ], 33 + ];
+62
resources/lang/kk-KZ/artist.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'page_description' => 'osu!-дағы таңдаулы әртістер', 8 + 'title' => 'Таңдаулы Әртістер', 9 + 10 + 'admin' => [ 11 + 'hidden' => 'ДӘЛ ҚАЗІР ӘРТІС ЖАСЫРЫН', 12 + ], 13 + 14 + 'beatmaps' => [ 15 + '_' => 'Карталар', 16 + 'download' => 'карта үлгісін жүктеу', 17 + 'download-na' => 'карта үлгісі әзірге қолжетімді емес', 18 + ], 19 + 20 + 'index' => [ 21 + 'description' => 'Таңдаулы әртістер osu!-ға жаңа да біртума музыканы әкелу мақсатында бізбен ынтымақтастықта жұмыс істейтін әртістер болып табылады. Бұл әртістер мен олардың өлеңдерінің топтамасы маппингке келетіндіктен және күшті болғандықтан osu! тобымен қолмен таңдалған. Осы таңдаулы әртістердің кейбірі тіпті osu!-ға арнайы жаңа өлеңдер шығарған.<br><br>Осы бөлімдегі барлық өлеңдер алдын-ала .osz файлдар ретінде берілген және osu! мен osu!-ға байланысты контентте қолдануға ресми лицензияланған.', 22 + ], 23 + 24 + 'links' => [ 25 + 'beatmaps' => 'osu! карталары', 26 + 'osu' => 'osu! профилі', 27 + 'site' => 'Ресми сайт', 28 + ], 29 + 30 + 'songs' => [ 31 + '_' => 'Өлеңдер', 32 + 'count' => ':count_delimited өлең|:count_delimited өлең', 33 + 'original' => 'osu!-ға арнайы', 34 + 'original_badge' => 'ORIGINAL', 35 + ], 36 + 37 + 'tracklist' => [ 38 + 'title' => 'атауы', 39 + 'length' => 'ұзақтығы', 40 + 'bpm' => 'bpm', 41 + 'genre' => 'жанры', 42 + ], 43 + 44 + 'tracks' => [ 45 + 'index' => [ 46 + '_' => 'өлең іздеу', 47 + 48 + 'form' => [ 49 + 'advanced' => 'Кең ауқымды Іздеу', 50 + 'album' => 'Альбом', 51 + 'artist' => 'Әртіс', 52 + 'bpm_gte' => 'Минималды BPM', 53 + 'bpm_lte' => 'Максималды BPM', 54 + 'empty' => 'Іздеу критерийлеріне келетін өлеңдер табылмады.', 55 + 'genre' => 'Жанры', 56 + 'genre_all' => 'Бәрі', 57 + 'length_gte' => 'Минималды Ұзақтығы', 58 + 'length_lte' => 'Максималды Ұзақтығы', 59 + ], 60 + ], 61 + ], 62 + ];
+189
resources/lang/kk-KZ/authorization.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'play_more' => 'Оданша osu! ойнап көрсеңіз қалай?', 8 + 'require_login' => 'Жалғастыру үшін аккаунтыңызға кіріңіз.', 9 + 'require_verification' => 'Жалғастыру үшін аккаунтыңызды растаңыз.', 10 + 'restricted' => "Құқыңыз шектеулі кезде бұны істей алмайсыз.", 11 + 'silenced' => "Бітеулі кезде бұны істей алмайсыз.", 12 + 'unauthorized' => 'Рұқсат жоқ.', 13 + 14 + 'beatmap_discussion' => [ 15 + 'destroy' => [ 16 + 'is_hype' => 'Хайпты болдырмау қолжетімді емес.', 17 + 'has_reply' => 'Жауаптары бар талқылауды өшіре алмайсыз', 18 + ], 19 + 'nominate' => [ 20 + 'exhausted' => 'Сіз өз номинация шегіне жеттіңіз, ертең қайта қайталап көріңіз.', 21 + 'incorrect_state' => 'Әрекетті орындауда қателік орын алды, бетті жаңартып көріңіз.', 22 + 'owner' => "Өз картаңызды номинаттай алмайсыз.", 23 + 'set_metadata' => 'Номинаттау алдында жанры мен тілін көрсету керексіз.', 24 + ], 25 + 'resolve' => [ 26 + 'not_owner' => 'Талқылауды тек оны бастаушы мен карта иесі шеше алады.', 27 + ], 28 + 29 + 'store' => [ 30 + 'mapper_note_wrong_user' => 'Тек карта иесі немесе номинаторы/NAT мүшесі маппер ескертулерін қалдыра алады.', 31 + ], 32 + 33 + 'vote' => [ 34 + 'bot' => "Ботпен жасалған талқылауға дауыс бере алмайсыз", 35 + 'limit_exceeded' => 'Көбірек дауыстар беру алдында кішкене күте тұрыңыз', 36 + 'owner' => "Өз талқылауыңызда дауыс бере алмайсыз.", 37 + 'wrong_beatmapset_state' => 'Тек қарастырылып жатқан карталардың талқылауларында ғана дауыс берсе болады.', 38 + ], 39 + ], 40 + 41 + 'beatmap_discussion_post' => [ 42 + 'destroy' => [ 43 + 'not_owner' => 'Тек өз хабарламаларыңызды жоя аласыз.', 44 + 'resolved' => 'Шешілген талқылаудағы постты жоя алмайсыз.', 45 + 'system_generated' => 'Автоматты түрде жасалған постты жоюға болмайды.', 46 + ], 47 + 48 + 'edit' => [ 49 + 'not_owner' => 'Тек пост авторы ғана постты өзгерте алады.', 50 + 'resolved' => 'Шешілген талқылаудағы постты өзгерте алмайсыз.', 51 + 'system_generated' => 'Автоматты түрде жасалған постты өзгертуге болмайды.', 52 + ], 53 + ], 54 + 55 + 'beatmapset' => [ 56 + 'discussion_locked' => 'Бұл картаның талқылауы жабық.', 57 + 58 + 'metadata' => [ 59 + 'nominated' => 'Сіз номинацияланған картаның метадеректерін өзгерте алмайсыз. Егер де ол қате орнатылған деп санасаңыз BN немесе NAT мүшесімен байланысқаныңыз жөн.', 60 + ], 61 + ], 62 + 63 + 'chat' => [ 64 + 'annnonce_only' => 'Бұл арна тек жарияларға арналған.', 65 + 'blocked' => 'Сізді бұғаттаған немесе сіз бұғаттаған қолданушыға жаза алмайсыз.', 66 + 'friends_only' => 'Қолданушы достары емес адамдардан келетін хабарламаларды бұғаттауда.', 67 + 'moderated' => 'Бұл арна дәл қазір модерациядан өтуде.', 68 + 'no_access' => 'Сізде бұл арнаға кіруге рұқсат жоқ.', 69 + 'receive_friends_only' => 'Қолданушы жауап бере алмауы мүмкін себебі сіз тек достарыңыздан ғана хабарламалар қабылдайсыз.', 70 + 'restricted' => 'Сіз бітелген, шектелген немесе бұғатталған кезде хабарламалар жібере алмайсыз.', 71 + 'silenced' => 'Сіз бітелген, шектелген немесе бұғатталған кезде хабарламалар жібере алмайсыз.', 72 + ], 73 + 74 + 'comment' => [ 75 + 'store' => [ 76 + 'disabled' => 'Пікірлер өшірулі', 77 + ], 78 + 'update' => [ 79 + 'deleted' => "Жойылған постты өзгертуге болмайды.", 80 + ], 81 + ], 82 + 83 + 'contest' => [ 84 + 'voting_over' => 'Дауыс беру мерзімі біткен соң берілген дауысыңызды өзгерте алмайсыз.', 85 + 86 + 'entry' => [ 87 + 'limit_reached' => 'Сіз осы сайыстың өтінім саны шегіне жеттіңіз ', 88 + 'over' => 'Өтінімдеріңіз үшін рақмет! Осы сайыс үшін өтінім қабылдау аяқталды және дауыс беру жақын арада ашылады.', 89 + ], 90 + ], 91 + 92 + 'forum' => [ 93 + 'moderate' => [ 94 + 'no_permission' => 'Бұл форумды модерациялауға құқыңыз жоқ.', 95 + ], 96 + 97 + 'post' => [ 98 + 'delete' => [ 99 + 'only_last_post' => 'Тек соңғы пост жойыла алады.', 100 + 'locked' => 'Жабық тақырыптағы постты жою мүмкін емес.', 101 + 'no_forum_access' => 'Сұралған форумға рұқсат қажет.', 102 + 'not_owner' => 'Тек пост авторы постты жоя алады.', 103 + ], 104 + 105 + 'edit' => [ 106 + 'deleted' => 'Жойылған постты өзгертуге болмайды.', 107 + 'locked' => 'Пост өзгертуден құлыпталған.', 108 + 'no_forum_access' => 'Сұралған форумға рұқсат қажет.', 109 + 'not_owner' => 'Тек пост авторы ғана постты өзгерте алады.', 110 + 'topic_locked' => 'Жабық тақырыптағы постты өзгерту мүмкін емес.', 111 + ], 112 + 113 + 'store' => [ 114 + 'play_more' => 'Форумға жазбастан бұрын ойынды ойнап көріңізші, өтініш! Егер ойынмен мәселелер болатын болса ол туралы "Көмек және Қолдау" форумына жазып көріңіз. ', 115 + 'too_many_help_posts' => "Сізге қосымша посттар жасамастан бұрын ойынды ойнау керек. Егер де cізде әлі де ойын ойнаумен мәселелер бар болса, support@ppy.sh поштасына жазыңыз", // FIXME: unhardcode email address. 116 + ], 117 + ], 118 + 119 + 'topic' => [ 120 + 'reply' => [ 121 + 'double_post' => 'Өтініш, қайта пост жасағанның орнына соңғы постыңызды өзгертіңіз.', 122 + 'locked' => 'Жабық тақырыпқа жауап беру мүмкін емес.', 123 + 'no_forum_access' => 'Сұралған форумға рұқсат қажет.', 124 + 'no_permission' => 'Жауап беруге құқыңыз жоқ.', 125 + 126 + 'user' => [ 127 + 'require_login' => 'Жауап беру үшін аккаунтыңызға кіріңіз.', 128 + 'restricted' => "Құқыңыз шектеулі кезде жауап бере алмайсыз.", 129 + 'silenced' => "Бітеулі кезде жауап бере алмайсыз.", 130 + ], 131 + ], 132 + 133 + 'store' => [ 134 + 'no_forum_access' => 'Сұралған форумға рұқсат қажет.', 135 + 'no_permission' => 'Жаңа тақырып құруға құқыңыз жоқ.', 136 + 'forum_closed' => 'Форум жабық және пост қабылдамайды.', 137 + ], 138 + 139 + 'vote' => [ 140 + 'no_forum_access' => 'Сұралған форумға рұқсат қажет.', 141 + 'over' => 'Сауалнама аяқталды және онда енді дауыс беруге болмайды.', 142 + 'play_more' => 'Форумда дауыс бермес бұрын көбірек ойнауыңыз керек.', 143 + 'voted' => 'Берілген дауысты өзгертуге тиым салынады.', 144 + 145 + 'user' => [ 146 + 'require_login' => 'Дауыс беру үшін аккаунтыңызға кіріңіз.', 147 + 'restricted' => "Құқыңыз шектеулі кезде дауыс бере алмайсыз.", 148 + 'silenced' => "Бітеулі кезде дауыс бере алмайсыз.", 149 + ], 150 + ], 151 + 152 + 'watch' => [ 153 + 'no_forum_access' => 'Сұралған форумға рұқсат қажет.', 154 + ], 155 + ], 156 + 157 + 'topic_cover' => [ 158 + 'edit' => [ 159 + 'uneditable' => 'Қате мұқаба көрсетілген.', 160 + 'not_owner' => 'Тек автор мұқабаны өзгерте алады.', 161 + ], 162 + 'store' => [ 163 + 'forum_not_allowed' => 'Бұл форум тақырып мұқаба суреттерді қабылдамайды.', 164 + ], 165 + ], 166 + 167 + 'view' => [ 168 + 'admin_only' => 'Бұл форумды тек әкімші көре алады.', 169 + ], 170 + ], 171 + 172 + 'score' => [ 173 + 'pin' => [ 174 + 'disabled_type' => "", 175 + 'not_owner' => 'Нәтиже иесі ғана ұпайды бекіте алады.', 176 + 'too_many' => 'Тым көп нәтиже бекітілді.', 177 + ], 178 + ], 179 + 180 + 'user' => [ 181 + 'page' => [ 182 + 'edit' => [ 183 + 'locked' => 'Пайдаланушы беті жабылған.', 184 + 'not_owner' => 'Тек жеке пайдаланушы бетін өзгертей алады.', 185 + 'require_supporter_tag' => 'osu!қолдаушысы тегі қажет.', 186 + ], 187 + ], 188 + ], 189 + ];
+25
resources/lang/kk-KZ/bbcode.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'bold' => 'Қалың қаріп', 8 + 'heading' => 'Басы', 9 + 'help' => 'Көмек', 10 + 'image' => 'Сурет', 11 + 'imagemap' => 'Сурет Картасы', 12 + 'italic' => 'Курсив', 13 + 'link' => 'Сілтеме', 14 + 'list' => 'Тізім', 15 + 'list_numbered' => 'Нөмірленген Тізім', 16 + 'size' => [ 17 + '_' => 'Қаріп өлшемі', 18 + 'tiny' => 'Өте кішкентай', 19 + 'small' => 'Кішкентай', 20 + 'normal' => 'Кәдімгідей', 21 + 'large' => 'Үлкен', 22 + ], 23 + 'spoilerbox' => 'Спойлер қорабы', 24 + 'strikethrough' => 'Сызып Тастау', 25 + ];
+15
resources/lang/kk-KZ/beatmap_discussion_posts.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'index' => [ 8 + 'title' => 'Карта пікірталас жазбалары', 9 + ], 10 + 11 + 'item' => [ 12 + 'content' => 'Мазмұны', 13 + 'modding_history_link' => 'Моддинг тарихын қарау', 14 + ], 15 + ];
+107
resources/lang/kk-KZ/beatmap_discussions.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'authorizations' => [ 8 + 'update' => [ 9 + 'null_user' => 'Өзгерту үшін жүйеге кіру керек.', 10 + 'system_generated' => 'Жүйе жасаған жазбаны өзгерту мүмкін емес.', 11 + 'wrong_user' => 'Өзгерту үшін жазбаның иесі болуы керек.', 12 + ], 13 + ], 14 + 15 + 'events' => [ 16 + 'empty' => 'Ештеңе болған жоқ... әлі.', 17 + ], 18 + 19 + 'index' => [ 20 + 'deleted_beatmap' => 'жойылған', 21 + 'none_found' => 'Бұл іздеу критерийлеріне сәйкес келетін пікірталастар табылмады.', 22 + 'title' => 'Карта пікірталастары', 23 + 24 + 'form' => [ 25 + '_' => 'Іздеу', 26 + 'deleted' => 'Жойылған пікірталастарды қосу', 27 + 'mode' => 'Карта режимі', 28 + 'only_unresolved' => 'Тек шешілмеген пікірталастарды көрсету', 29 + 'types' => 'Хабарламаның түрлері', 30 + 'username' => 'Пайдаланушы аты', 31 + 32 + 'beatmapset_status' => [ 33 + '_' => 'Картаның Күйі', 34 + 'all' => 'Бәрі', 35 + 'disqualified' => 'Дисквалификация жасалған', 36 + 'never_qualified' => 'Ешқашан Квалификация алмаған', 37 + 'qualified' => 'Квалификация алған', 38 + 'ranked' => 'Рейтингілік', 39 + ], 40 + 41 + 'user' => [ 42 + 'label' => 'Пайдаланушы', 43 + 'overview' => 'Әрекеттерге шолу', 44 + ], 45 + ], 46 + ], 47 + 48 + 'item' => [ 49 + 'created_at' => 'Жазба күні', 50 + 'deleted_at' => 'Жою күні', 51 + 'message_type' => 'Түрі', 52 + 'permalink' => 'Тұрақты Сілтеме', 53 + ], 54 + 55 + 'nearby_posts' => [ 56 + 'confirm' => 'Жазбалардың ешқайсысы менің сұрағыма қатыспайды', 57 + 'notice' => ':timestamp (:existing_timestamps) ішінде жазбалар бар. Жазу алдында оларды тексеріңіз.', 58 + 'unsaved' => ':count қарауда ', 59 + ], 60 + 61 + 'owner_editor' => [ 62 + 'button' => 'Деңгей иесі', 63 + 'reset_confirm' => 'Осы деңгей үшін иесін қалпына келтіру керек пе?', 64 + 'user' => 'Иесі', 65 + 'version' => 'Деңгейі', 66 + ], 67 + 68 + 'reply' => [ 69 + 'open' => [ 70 + 'guest' => 'Жауап беру үшін жүйеге кіріңіз', 71 + 'user' => 'Жауап беру', 72 + ], 73 + ], 74 + 75 + 'review' => [ 76 + 'block_count' => ':used / :max блоктар қолданылған', 77 + 'go_to_parent' => 'Қараудың жазбаны көру', 78 + 'go_to_child' => 'Пікірталасты көру', 79 + 'validation' => [ 80 + 'block_too_large' => 'әр блокта тек :limit таңбаларына дейін болуы мүмкін', 81 + 'external_references' => 'қарауда осы қарауға жатпайтын мәселелерге сілтемелер бар', 82 + 'invalid_block_type' => 'жарамсыз блоктың түрі', 83 + 'invalid_document' => 'жарамсыз қарау', 84 + 'invalid_discussion_type' => 'жарамсыз пікірталас түрі', 85 + 'minimum_issues' => 'қарауда ең аз :count мәселе болуы керек| қарауда ең аз :count мәселелері болуы керек', 86 + 'missing_text' => 'блокта мәтін жоқ', 87 + 'too_many_blocks' => 'қарауда тек :count параграф/мәселе болуы мүмкін|қарауда тек :count параграфтар/мәселелер болуы мүмкін', 88 + ], 89 + ], 90 + 91 + 'system' => [ 92 + 'resolved' => [ 93 + 'true' => ':user шешкен деп белгіленген', 94 + 'false' => ':user-ден қайта ашылды', 95 + ], 96 + ], 97 + 98 + 'timestamp_display' => [ 99 + 'general' => 'негізгі', 100 + 'general_all' => 'негізгі (барлығы)', 101 + ], 102 + 103 + 'user_filter' => [ 104 + 'everyone' => 'Әркім', 105 + 'label' => 'Пайдаланушы бойынша іріктеу', 106 + ], 107 + ];
+49
resources/lang/kk-KZ/beatmappacks.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'index' => [ 8 + 'description' => '', 9 + 'empty' => '', 10 + 'nav_title' => '', 11 + 'title' => '', 12 + 13 + 'blurb' => [ 14 + 'important' => '', 15 + 'install_instruction' => '', 16 + 'note' => [ 17 + '_' => '', 18 + 'scary' => '', 19 + ], 20 + ], 21 + ], 22 + 23 + 'show' => [ 24 + 'download' => '', 25 + 'item' => [ 26 + 'cleared' => '', 27 + 'not_cleared' => '', 28 + ], 29 + 'no_diff_reduction' => [ 30 + '_' => '', 31 + 'link' => '', 32 + ], 33 + ], 34 + 35 + 'mode' => [ 36 + 'artist' => '', 37 + 'chart' => '', 38 + 'featured' => '', 39 + 'loved' => '', 40 + 'standard' => '', 41 + 'theme' => '', 42 + 'tournament' => '', 43 + ], 44 + 45 + 'require_login' => [ 46 + '_' => '', 47 + 'link_text' => '', 48 + ], 49 + ];
+356
resources/lang/kk-KZ/beatmaps.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'discussion-votes' => [ 8 + 'update' => [ 9 + 'error' => '', 10 + ], 11 + ], 12 + 13 + 'discussions' => [ 14 + 'allow_kudosu' => '', 15 + 'beatmap_information' => '', 16 + 'delete' => '', 17 + 'deleted' => '', 18 + 'deny_kudosu' => '', 19 + 'edit' => '', 20 + 'edited' => '', 21 + 'guest' => '', 22 + 'kudosu_denied' => '', 23 + 'message_placeholder_deleted_beatmap' => '', 24 + 'message_placeholder_locked' => '', 25 + 'message_placeholder_silenced' => "", 26 + 'message_type_select' => '', 27 + 'reply_notice' => '', 28 + 'reply_placeholder' => '', 29 + 'require-login' => '', 30 + 'resolved' => '', 31 + 'restore' => '', 32 + 'show_deleted' => '', 33 + 'title' => '', 34 + 35 + 'collapse' => [ 36 + 'all-collapse' => '', 37 + 'all-expand' => '', 38 + ], 39 + 40 + 'empty' => [ 41 + 'empty' => '', 42 + 'hidden' => '', 43 + ], 44 + 45 + 'lock' => [ 46 + 'button' => [ 47 + 'lock' => '', 48 + 'unlock' => '', 49 + ], 50 + 51 + 'prompt' => [ 52 + 'lock' => '', 53 + 'unlock' => '', 54 + ], 55 + ], 56 + 57 + 'message_hint' => [ 58 + 'in_general' => '', 59 + 'in_timeline' => '', 60 + ], 61 + 62 + 'message_placeholder' => [ 63 + 'general' => '', 64 + 'generalAll' => '', 65 + 'review' => '', 66 + 'timeline' => '', 67 + ], 68 + 69 + 'message_type' => [ 70 + 'disqualify' => '', 71 + 'hype' => '', 72 + 'mapper_note' => '', 73 + 'nomination_reset' => '', 74 + 'praise' => '', 75 + 'problem' => '', 76 + 'problem_warning' => '', 77 + 'review' => '', 78 + 'suggestion' => '', 79 + ], 80 + 81 + 'mode' => [ 82 + 'events' => '', 83 + 'general' => '', 84 + 'reviews' => '', 85 + 'timeline' => '', 86 + 'scopes' => [ 87 + 'general' => '', 88 + 'generalAll' => '', 89 + ], 90 + ], 91 + 92 + 'new' => [ 93 + 'pin' => '', 94 + 'timestamp' => '', 95 + 'timestamp_missing' => '', 96 + 'title' => '', 97 + 'unpin' => '', 98 + ], 99 + 100 + 'review' => [ 101 + 'new' => '', 102 + 'embed' => [ 103 + 'delete' => '', 104 + 'missing' => '', 105 + 'unlink' => '', 106 + 'unsaved' => '', 107 + 'timestamp' => [ 108 + 'all-diff' => '', 109 + 'diff' => '', 110 + ], 111 + ], 112 + 'insert-block' => [ 113 + 'paragraph' => '', 114 + 'praise' => '', 115 + 'problem' => '', 116 + 'suggestion' => '', 117 + ], 118 + ], 119 + 120 + 'show' => [ 121 + 'title' => '', 122 + ], 123 + 124 + 'sort' => [ 125 + 'created_at' => '', 126 + 'timeline' => '', 127 + 'updated_at' => '', 128 + ], 129 + 130 + 'stats' => [ 131 + 'deleted' => '', 132 + 'mapper_notes' => '', 133 + 'mine' => '', 134 + 'pending' => '', 135 + 'praises' => '', 136 + 'resolved' => '', 137 + 'total' => '', 138 + ], 139 + 140 + 'status-messages' => [ 141 + 'approved' => '', 142 + 'graveyard' => "", 143 + 'loved' => '', 144 + 'ranked' => '', 145 + 'wip' => '', 146 + ], 147 + 148 + 'votes' => [ 149 + 'none' => [ 150 + 'down' => '', 151 + 'up' => '', 152 + ], 153 + 'latest' => [ 154 + 'down' => '', 155 + 'up' => '', 156 + ], 157 + ], 158 + ], 159 + 160 + 'hype' => [ 161 + 'button' => '', 162 + 'button_done' => '', 163 + 'confirm' => "", 164 + 'explanation' => '', 165 + 'explanation_guest' => '', 166 + 'new_time' => "", 167 + 'remaining' => '', 168 + 'required_text' => '', 169 + 'section_title' => '', 170 + 'title' => '', 171 + ], 172 + 173 + 'feedback' => [ 174 + 'button' => '', 175 + ], 176 + 177 + 'nominations' => [ 178 + 'already_nominated' => '', 179 + 'cannot_nominate' => '', 180 + 'delete' => '', 181 + 'delete_own_confirm' => '', 182 + 'delete_other_confirm' => '', 183 + 'disqualification_prompt' => '', 184 + 'disqualified_at' => '', 185 + 'disqualified_no_reason' => '', 186 + 'disqualify' => '', 187 + 'incorrect_state' => '', 188 + 'love' => '', 189 + 'love_choose' => '', 190 + 'love_confirm' => '', 191 + 'nominate' => '', 192 + 'nominate_confirm' => '', 193 + 'nominated_by' => '', 194 + 'not_enough_hype' => "", 195 + 'remove_from_loved' => '', 196 + 'remove_from_loved_prompt' => '', 197 + 'required_text' => '', 198 + 'reset_message_deleted' => '', 199 + 'title' => '', 200 + 'unresolved_issues' => '', 201 + 202 + 'rank_estimate' => [ 203 + '_' => '', 204 + 'on' => '', 205 + 'queue' => '', 206 + 'soon' => '', 207 + ], 208 + 209 + 'reset_at' => [ 210 + 'nomination_reset' => '', 211 + 'disqualify' => '', 212 + ], 213 + 214 + 'reset_confirm' => [ 215 + 'disqualify' => '', 216 + 'nomination_reset' => '', 217 + 'problem_warning' => '', 218 + ], 219 + ], 220 + 221 + 'listing' => [ 222 + 'search' => [ 223 + 'prompt' => '', 224 + 'login_required' => '', 225 + 'options' => '', 226 + 'supporter_filter' => '', 227 + 'not-found' => '', 228 + 'not-found-quote' => '', 229 + 'filters' => [ 230 + 'extra' => '', 231 + 'general' => '', 232 + 'genre' => '', 233 + 'language' => '', 234 + 'mode' => '', 235 + 'nsfw' => '', 236 + 'played' => '', 237 + 'rank' => '', 238 + 'status' => '', 239 + ], 240 + 'sorting' => [ 241 + 'title' => '', 242 + 'artist' => '', 243 + 'difficulty' => '', 244 + 'favourites' => '', 245 + 'updated' => '', 246 + 'ranked' => '', 247 + 'rating' => '', 248 + 'plays' => '', 249 + 'relevance' => '', 250 + 'nominations' => '', 251 + ], 252 + 'supporter_filter_quote' => [ 253 + '_' => '', 254 + 'link_text' => '', 255 + ], 256 + ], 257 + ], 258 + 'general' => [ 259 + 'converts' => '', 260 + 'featured_artists' => '', 261 + 'follows' => '', 262 + 'recommended' => '', 263 + 'spotlights' => '', 264 + ], 265 + 'mode' => [ 266 + 'all' => '', 267 + 'any' => '', 268 + 'osu' => '', 269 + 'taiko' => '', 270 + 'fruits' => '', 271 + 'mania' => '', 272 + ], 273 + 'status' => [ 274 + 'any' => '', 275 + 'approved' => '', 276 + 'favourites' => '', 277 + 'graveyard' => '', 278 + 'leaderboard' => '', 279 + 'loved' => '', 280 + 'mine' => '', 281 + 'pending' => '', 282 + 'wip' => '', 283 + 'qualified' => '', 284 + 'ranked' => '', 285 + ], 286 + 'genre' => [ 287 + 'any' => '', 288 + 'unspecified' => '', 289 + 'video-game' => '', 290 + 'anime' => '', 291 + 'rock' => '', 292 + 'pop' => '', 293 + 'other' => '', 294 + 'novelty' => '', 295 + 'hip-hop' => '', 296 + 'electronic' => '', 297 + 'metal' => '', 298 + 'classical' => '', 299 + 'folk' => '', 300 + 'jazz' => '', 301 + ], 302 + 'language' => [ 303 + 'any' => '', 304 + 'english' => '', 305 + 'chinese' => '', 306 + 'french' => '', 307 + 'german' => '', 308 + 'italian' => '', 309 + 'japanese' => '', 310 + 'korean' => '', 311 + 'spanish' => '', 312 + 'swedish' => '', 313 + 'russian' => '', 314 + 'polish' => '', 315 + 'instrumental' => '', 316 + 'other' => '', 317 + 'unspecified' => '', 318 + ], 319 + 320 + 'nsfw' => [ 321 + 'exclude' => '', 322 + 'include' => '', 323 + ], 324 + 325 + 'played' => [ 326 + 'any' => '', 327 + 'played' => '', 328 + 'unplayed' => '', 329 + ], 330 + 'extra' => [ 331 + 'video' => '', 332 + 'storyboard' => '', 333 + ], 334 + 'rank' => [ 335 + 'any' => '', 336 + 'XH' => '', 337 + 'X' => '', 338 + 'SH' => '', 339 + 'S' => '', 340 + 'A' => '', 341 + 'B' => '', 342 + 'C' => '', 343 + 'D' => '', 344 + ], 345 + 'panel' => [ 346 + 'playcount' => '', 347 + 'favourites' => '', 348 + ], 349 + 'variant' => [ 350 + 'mania' => [ 351 + '4k' => '', 352 + '7k' => '', 353 + 'all' => '', 354 + ], 355 + ], 356 + ];
+14
resources/lang/kk-KZ/beatmapset_discussion_votes.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'index' => [ 8 + 'title' => 'Карта пікірталас дауыстары', 9 + ], 10 + 11 + 'item' => [ 12 + 'score' => 'Нәтиже', 13 + ], 14 + ];
+87
resources/lang/kk-KZ/beatmapset_events.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'event' => [ 8 + 'approve' => 'Қабылданған.', 9 + 'beatmap_owner_change' => 'Деңгейдің иесі :beatmap пайдаланушыдан :new_user пайдаланушыға болып өзгерілді.', 10 + 'discussion_delete' => 'Модератор :discussion пікірталасты жойды.', 11 + 'discussion_lock' => 'Бұл карта үшін пікірталас өшірілген. (:text)', 12 + 'discussion_post_delete' => 'Модератор :discussion пікірталаста жазбаны жойды.', 13 + 'discussion_post_restore' => 'Модератор :discussion пікірталаста жазбаны қалпына келтірді.', 14 + 'discussion_restore' => 'Модератор :discussion пікірталасты қалпына келтірді.', 15 + 'discussion_unlock' => '', 16 + 'disqualify' => '', 17 + 'disqualify_legacy' => '', 18 + 'genre_edit' => '', 19 + 'issue_reopen' => '', 20 + 'issue_resolve' => '', 21 + 'kudosu_allow' => '', 22 + 'kudosu_deny' => '', 23 + 'kudosu_gain' => '', 24 + 'kudosu_lost' => '', 25 + 'kudosu_recalculate' => '', 26 + 'language_edit' => '', 27 + 'love' => '', 28 + 'nominate' => '', 29 + 'nominate_modes' => '', 30 + 'nomination_reset' => '', 31 + 'nomination_reset_received' => '', 32 + 'nomination_reset_received_profile' => '', 33 + 'offset_edit' => '', 34 + 'qualify' => '', 35 + 'rank' => 'Рейтингілік.', 36 + 'remove_from_loved' => ':user Ұнамдын ішінен жойды. (:text)', 37 + 'tags_edit' => 'Тегтер ":old"-тен ":new"-ке өзгертілді.', 38 + 39 + 'nsfw_toggle' => [ 40 + 'to_0' => 'Былапыт тегі жойылды', 41 + 'to_1' => 'Былапыт тегі қойылған', 42 + ], 43 + ], 44 + 45 + 'index' => [ 46 + 'title' => 'Карты жинақтың оқиғалары', 47 + 48 + 'form' => [ 49 + 'period' => 'Мерзім', 50 + 'types' => 'Түрлері', 51 + ], 52 + ], 53 + 54 + 'item' => [ 55 + 'content' => 'Мазмұны', 56 + 'discussion_deleted' => '[deleted]', 57 + 'type' => 'Түрі', 58 + ], 59 + 60 + 'type' => [ 61 + 'approve' => 'Қабылдауы', 62 + 'beatmap_owner_change' => 'Нәтиже иесінің өзгертуі', 63 + 'discussion_delete' => 'Пікірталастың жоюы', 64 + 'discussion_post_delete' => '', 65 + 'discussion_post_restore' => '', 66 + 'discussion_restore' => '', 67 + 'disqualify' => '', 68 + 'genre_edit' => '', 69 + 'issue_reopen' => '', 70 + 'issue_resolve' => '', 71 + 'kudosu_allow' => '', 72 + 'kudosu_deny' => '', 73 + 'kudosu_gain' => '', 74 + 'kudosu_lost' => '', 75 + 'kudosu_recalculate' => '', 76 + 'language_edit' => '', 77 + 'love' => 'Ұнамды статусын беру', 78 + 'nominate' => 'Номинация', 79 + 'nomination_reset' => '', 80 + 'nomination_reset_received' => '', 81 + 'nsfw_toggle' => 'Былапыт тегі', 82 + 'offset_edit' => 'Оффсет өзгертуі', 83 + 'qualify' => 'Квалификация', 84 + 'rank' => 'Рейтинг беру', 85 + 'remove_from_loved' => 'Ұнамды статусын жоюы', 86 + ], 87 + ];
+29
resources/lang/kk-KZ/beatmapset_watches.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'index' => [ 8 + 'description' => '', 9 + 'title_compact' => '', 10 + 11 + 'counts' => [ 12 + 'total' => '', 13 + 'unread' => '', 14 + ], 15 + 16 + 'table' => [ 17 + 'empty' => '', 18 + 'last_update' => '', 19 + 'open_issues' => '', 20 + 'state' => '', 21 + 'title' => '', 22 + ], 23 + ], 24 + 25 + 'status' => [ 26 + 'read' => '', 27 + 'unread' => '', 28 + ], 29 + ];
+228
resources/lang/kk-KZ/beatmapsets.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'availability' => [ 8 + 'disabled' => '', 9 + 'parts-removed' => '', 10 + 'more-info' => '', 11 + 'rule_violation' => '', 12 + ], 13 + 14 + 'cover' => [ 15 + 'deleted' => '', 16 + ], 17 + 18 + 'download' => [ 19 + 'limit_exceeded' => '', 20 + ], 21 + 22 + 'featured_artist_badge' => [ 23 + 'label' => '', 24 + ], 25 + 26 + 'index' => [ 27 + 'title' => '', 28 + 'guest_title' => '', 29 + ], 30 + 31 + 'panel' => [ 32 + 'empty' => '', 33 + 34 + 'download' => [ 35 + 'all' => '', 36 + 'video' => '', 37 + 'no_video' => '', 38 + 'direct' => '', 39 + ], 40 + ], 41 + 42 + 'nominate' => [ 43 + 'hybrid_requires_modes' => '', 44 + 'incorrect_mode' => '', 45 + 'full_bn_required' => '', 46 + 'too_many' => '', 47 + 48 + 'dialog' => [ 49 + 'confirmation' => '', 50 + 'header' => '', 51 + 'hybrid_warning' => '', 52 + 'which_modes' => '', 53 + ], 54 + ], 55 + 56 + 'nsfw_badge' => [ 57 + 'label' => '', 58 + ], 59 + 60 + 'show' => [ 61 + 'discussion' => '', 62 + 63 + 'deleted_banner' => [ 64 + 'title' => '', 65 + 'message' => '', 66 + ], 67 + 68 + 'details' => [ 69 + 'by_artist' => '', 70 + 'favourite' => '', 71 + 'favourite_login' => '', 72 + 'logged-out' => '', 73 + 'mapped_by' => '', 74 + 'mapped_by_guest' => '', 75 + 'unfavourite' => '', 76 + 'updated_timeago' => '', 77 + 78 + 'download' => [ 79 + '_' => '', 80 + 'direct' => '', 81 + 'no-video' => '', 82 + 'video' => '', 83 + ], 84 + 85 + 'login_required' => [ 86 + 'bottom' => '', 87 + 'top' => '', 88 + ], 89 + ], 90 + 91 + 'details_date' => [ 92 + 'approved' => '', 93 + 'loved' => '', 94 + 'qualified' => '', 95 + 'ranked' => '', 96 + 'submitted' => '', 97 + 'updated' => '', 98 + ], 99 + 100 + 'favourites' => [ 101 + 'limit_reached' => '', 102 + ], 103 + 104 + 'hype' => [ 105 + 'action' => '', 106 + 107 + 'current' => [ 108 + '_' => '', 109 + 110 + 'status' => [ 111 + 'pending' => '', 112 + 'qualified' => '', 113 + 'wip' => '', 114 + ], 115 + ], 116 + 117 + 'disqualify' => [ 118 + '_' => '', 119 + ], 120 + 121 + 'report' => [ 122 + '_' => '', 123 + 'button' => '', 124 + 'link' => '', 125 + ], 126 + ], 127 + 128 + 'info' => [ 129 + 'description' => '', 130 + 'genre' => '', 131 + 'language' => '', 132 + 'no_scores' => '', 133 + 'nominators' => '', 134 + 'nsfw' => '', 135 + 'offset' => '', 136 + 'points-of-failure' => '', 137 + 'source' => '', 138 + 'storyboard' => '', 139 + 'success-rate' => '', 140 + 'tags' => '', 141 + 'video' => '', 142 + ], 143 + 144 + 'nsfw_warning' => [ 145 + 'details' => '', 146 + 'title' => '', 147 + 148 + 'buttons' => [ 149 + 'disable' => '', 150 + 'listing' => '', 151 + 'show' => '', 152 + ], 153 + ], 154 + 155 + 'scoreboard' => [ 156 + 'achieved' => '', 157 + 'country' => '', 158 + 'error' => '', 159 + 'friend' => '', 160 + 'global' => '', 161 + 'supporter-link' => '', 162 + 'supporter-only' => '', 163 + 'title' => '', 164 + 165 + 'headers' => [ 166 + 'accuracy' => '', 167 + 'combo' => '', 168 + 'miss' => '', 169 + 'mods' => '', 170 + 'pin' => '', 171 + 'player' => '', 172 + 'pp' => '', 173 + 'rank' => '', 174 + 'score' => '', 175 + 'score_total' => '', 176 + 'time' => '', 177 + ], 178 + 179 + 'no_scores' => [ 180 + 'country' => '', 181 + 'friend' => '', 182 + 'global' => '', 183 + 'loading' => '', 184 + 'unranked' => '', 185 + ], 186 + 'score' => [ 187 + 'first' => '', 188 + 'own' => '', 189 + ], 190 + 'supporter_link' => [ 191 + '_' => '', 192 + 'here' => '', 193 + ], 194 + ], 195 + 196 + 'stats' => [ 197 + 'cs' => '', 198 + 'cs-mania' => '', 199 + 'drain' => '', 200 + 'accuracy' => '', 201 + 'ar' => '', 202 + 'stars' => '', 203 + 'total_length' => '', 204 + 'bpm' => '', 205 + 'count_circles' => '', 206 + 'count_sliders' => '', 207 + 'offset' => '', 208 + 'user-rating' => '', 209 + 'rating-spread' => '', 210 + 'nominations' => '', 211 + 'playcount' => '', 212 + ], 213 + 214 + 'status' => [ 215 + 'ranked' => '', 216 + 'approved' => '', 217 + 'loved' => '', 218 + 'qualified' => '', 219 + 'wip' => '', 220 + 'pending' => '', 221 + 'graveyard' => '', 222 + ], 223 + ], 224 + 225 + 'spotlight_badge' => [ 226 + 'label' => '', 227 + ], 228 + ];
+40
resources/lang/kk-KZ/changelog.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'generic' => '', 8 + 9 + 'build' => [ 10 + 'title' => '', 11 + ], 12 + 13 + 'builds' => [ 14 + 'users_online' => '', 15 + ], 16 + 17 + 'entry' => [ 18 + 'by' => '', 19 + ], 20 + 21 + 'index' => [ 22 + 'page_title' => [ 23 + '_' => '', 24 + '_from' => '', 25 + '_from_to' => '', 26 + '_stream' => '', 27 + '_stream_from' => '', 28 + '_stream_from_to' => '', 29 + '_stream_to' => '', 30 + '_to' => '', 31 + ], 32 + ], 33 + 34 + 'support' => [ 35 + 'heading' => '', 36 + 'text_1' => '', 37 + 'text_1_link' => '', 38 + 'text_2' => '', 39 + ], 40 + ];
+63
resources/lang/kk-KZ/chat.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'loading_users' => '', 8 + 'talking_in' => '', 9 + 'talking_with' => '', 10 + 'title_compact' => '', 11 + 'unread_messages' => '', 12 + 13 + 'cannot_send' => [ 14 + 'channel' => '', 15 + 'user' => '', 16 + ], 17 + 18 + 'channels' => [ 19 + 'confirm_part' => '', 20 + 'create' => '', 21 + 22 + 'list' => [ 23 + 'title' => [ 24 + 'ANNOUNCE' => '', 25 + 'GROUP' => '', 26 + 'PM' => '', 27 + 'PUBLIC' => '', 28 + ], 29 + ], 30 + ], 31 + 32 + 'form' => [ 33 + 'title' => [ 34 + 'announcement' => '', 35 + ], 36 + 37 + 'labels' => [ 38 + 'description' => '', 39 + 'message' => '', 40 + 'name' => '', 41 + 'users' => '', 42 + ], 43 + ], 44 + 45 + 'not_found' => [ 46 + 'message' => '', 47 + 'title' => '', 48 + ], 49 + 50 + 'input' => [ 51 + 'create' => '', 52 + 'disabled' => '', 53 + 'disconnected' => '', 54 + 'placeholder' => '', 55 + 'send' => '', 56 + ], 57 + 58 + 'no-conversations' => [ 59 + 'howto' => "", 60 + 'lazer' => '', 61 + 'title' => '', 62 + ], 63 + ];
+18
resources/lang/kk-KZ/client_verifications.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'completed' => [ 8 + 'home' => '', 9 + 'logout' => '', 10 + 'text' => '', 11 + 'title' => '', 12 + ], 13 + 14 + 'create' => [ 15 + 'confirm' => '', 16 + 'title' => '', 17 + ], 18 + ];
+55
resources/lang/kk-KZ/comments.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'deleted' => '', 8 + 'deleted_by' => '', 9 + 'deleted_by_system' => '', 10 + 'deleted_count' => '', 11 + 'edited' => '', 12 + 'pinned' => '', 13 + 'empty' => '', 14 + 'empty_other' => '', 15 + 'load_replies' => '', 16 + 'replies_count' => '', 17 + 'title' => '', 18 + 19 + 'commentable_name' => [ 20 + 'beatmapset' => '', 21 + 'build' => '', 22 + 'news_post' => '', 23 + '_deleted' => '', 24 + ], 25 + 26 + 'editor' => [ 27 + 'textarea_hint' => [ 28 + '_' => '', 29 + 'edit' => '', 30 + 'new' => '', 31 + 'reply' => '', 32 + ], 33 + ], 34 + 35 + 'guest_button' => [ 36 + 'new' => '', 37 + 'reply' => '', 38 + ], 39 + 40 + 'index' => [ 41 + 'nav_comments' => '', 42 + 'nav_title' => '', 43 + 'no_comments' => '', 44 + ], 45 + 46 + 'placeholder' => [ 47 + 'edit' => '', 48 + 'new' => '', 49 + 'reply' => '', 50 + ], 51 + 52 + 'show' => [ 53 + 'nav_title' => '', 54 + ], 55 + ];
+163
resources/lang/kk-KZ/common.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'confirmation' => '', 8 + 'confirmation_unsaved' => '', 9 + 'saved' => '', 10 + 11 + 'array_and' => [ 12 + 'words_connector' => '', 13 + 'two_words_connector' => '', 14 + 'last_word_connector' => '', 15 + ], 16 + 17 + 'badges' => [ 18 + 'new' => '', 19 + ], 20 + 21 + 'buttons' => [ 22 + 'admin' => '', 23 + 'authorise' => '', 24 + 'authorising' => '', 25 + 'back_to_previous' => '', 26 + 'back_to_top' => '', 27 + 'cancel' => '', 28 + 'change' => '', 29 + 'clear' => '', 30 + 'click_to_copy' => '', 31 + 'click_to_copy_copied' => '', 32 + 'close' => '', 33 + 'collapse' => '', 34 + 'delete' => '', 35 + 'edit' => '', 36 + 'expand' => '', 37 + 'hide' => '', 38 + 'permalink' => '', 39 + 'pin' => '', 40 + 'post' => '', 41 + 'read_more' => '', 42 + 'reply' => '', 43 + 'reply_reopen' => '', 44 + 'reply_resolve' => '', 45 + 'reset' => '', 46 + 'restore' => '', 47 + 'retry' => '', 48 + 'save' => '', 49 + 'saving' => '', 50 + 'search' => '', 51 + 'see_more' => '', 52 + 'show' => '', 53 + 'show_deleted' => '', 54 + 'show_less' => '', 55 + 'show_more' => '', 56 + 'show_more_options' => '', 57 + 'submit' => '', 58 + 'unpin' => '', 59 + 'update' => '', 60 + 'upload_image' => '', 61 + 62 + 'watch' => [ 63 + 'to_0' => '', 64 + 'to_1' => '', 65 + ], 66 + ], 67 + 68 + 'count' => [ 69 + 'badges' => '', 70 + 'days' => '', 71 + 'hour_short_unit' => '', 72 + 'hours' => '', 73 + 'item' => '', 74 + 'minute_short_unit' => '', 75 + 'minutes' => '', 76 + 'months' => '', 77 + 'notifications' => '', 78 + 'plus_others' => '', 79 + 'post' => '', 80 + 'second_short_unit' => '', 81 + 'star_priority' => '', 82 + 'update' => '', 83 + 'view' => '', 84 + 'years' => '', 85 + ], 86 + 87 + 'countdown' => [ 88 + 'days' => '', 89 + 'hours' => '', 90 + 'minutes' => '', 91 + 'seconds' => '', 92 + ], 93 + 94 + 'datetime' => [ 95 + 'year_month' => [ 96 + 'moment' => '', 97 + 'php' => '', 98 + ], 99 + 'year_month_short' => [ 100 + 'moment' => '', 101 + ], 102 + ], 103 + 104 + 'device' => [ 105 + 'keyboard' => '', 106 + 'mouse' => '', 107 + 'tablet' => '', 108 + 'touch' => '', 109 + ], 110 + 111 + 'dropzone' => [ 112 + 'target' => '', 113 + ], 114 + 115 + 'input' => [ 116 + 'search' => '', 117 + ], 118 + 119 + 'pagination' => [ 120 + 'previous' => '', 121 + 'next' => '', 122 + ], 123 + 124 + 'score_count' => [ 125 + 'count_100' => '', 126 + 'count_300' => '', 127 + 'count_50' => '', 128 + 'count_geki' => '', 129 + 'count_katu' => '', 130 + 'count_miss' => '', 131 + ], 132 + 133 + 'scoreboard_time' => [ 134 + 'd' => '', 135 + 'dd' => '', 136 + 'h' => '', 137 + 'hh' => '', 138 + 'm' => '', 139 + 'mm' => '', 140 + 'month' => '', 141 + 'months' => '', 142 + 'past' => '', 143 + 's' => '', 144 + 'y' => '', 145 + 'yy' => '', 146 + ], 147 + 148 + 'time' => [ 149 + 'days_ago' => '', 150 + 'hours_ago' => '', 151 + 'now' => '', 152 + 'remaining' => '', 153 + ], 154 + 155 + 'title' => [ 156 + 'notice' => '', 157 + ], 158 + 159 + 'wrong_user' => [ 160 + '_' => '', 161 + 'logout_link' => '', 162 + ], 163 + ];
+148
resources/lang/kk-KZ/community.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'support' => [ 8 + 'convinced' => [ 9 + 'title' => '', 10 + 'support' => '', 11 + 'gift' => '', 12 + 'instructions' => '', 13 + ], 14 + 'why-support' => [ 15 + 'title' => '', 16 + 17 + 'team' => [ 18 + 'title' => '', 19 + 'description' => '', 20 + ], 21 + 'infra' => [ 22 + 'title' => '', 23 + 'description' => '', 24 + ], 25 + 'featured-artists' => [ 26 + 'title' => '', 27 + 'description' => '', 28 + 'link_text' => '', 29 + ], 30 + 'ads' => [ 31 + 'title' => '', 32 + 'description' => '', 33 + ], 34 + 'tournaments' => [ 35 + 'title' => '', 36 + 'description' => '', 37 + 'link_text' => '', 38 + ], 39 + 'bounty-program' => [ 40 + 'title' => '', 41 + 'description' => '', 42 + 'link_text' => '', 43 + ], 44 + ], 45 + 'perks' => [ 46 + 'title' => '', 47 + 'osu_direct' => [ 48 + 'title' => '', 49 + 'description' => '', 50 + ], 51 + 52 + 'friend_ranking' => [ 53 + 'title' => '', 54 + 'description' => "", 55 + ], 56 + 57 + 'country_ranking' => [ 58 + 'title' => '', 59 + 'description' => '', 60 + ], 61 + 62 + 'mod_filtering' => [ 63 + 'title' => '', 64 + 'description' => '', 65 + ], 66 + 67 + 'auto_downloads' => [ 68 + 'title' => '', 69 + 'description' => '', 70 + ], 71 + 72 + 'upload_more' => [ 73 + 'title' => '', 74 + 'description' => '', 75 + ], 76 + 77 + 'early_access' => [ 78 + 'title' => '', 79 + 'description' => '', 80 + ], 81 + 82 + 'customisation' => [ 83 + 'title' => '', 84 + 'description' => "", 85 + ], 86 + 87 + 'beatmap_filters' => [ 88 + 'title' => '', 89 + 'description' => '', 90 + ], 91 + 92 + 'yellow_fellow' => [ 93 + 'title' => '', 94 + 'description' => '', 95 + ], 96 + 97 + 'speedy_downloads' => [ 98 + 'title' => '', 99 + 'description' => '', 100 + ], 101 + 102 + 'change_username' => [ 103 + 'title' => '', 104 + 'description' => '', 105 + ], 106 + 107 + 'skinnables' => [ 108 + 'title' => '', 109 + 'description' => '', 110 + ], 111 + 112 + 'feature_votes' => [ 113 + 'title' => '', 114 + 'description' => '', 115 + ], 116 + 117 + 'sort_options' => [ 118 + 'title' => '', 119 + 'description' => '', 120 + ], 121 + 122 + 'more_favourites' => [ 123 + 'title' => '', 124 + 'description' => '', 125 + ], 126 + 'more_friends' => [ 127 + 'title' => '', 128 + 'description' => '', 129 + ], 130 + 'more_beatmaps' => [ 131 + 'title' => '', 132 + 'description' => '', 133 + ], 134 + 'friend_filtering' => [ 135 + 'title' => '', 136 + 'description' => '', 137 + ], 138 + 139 + ], 140 + 'supporter_status' => [ 141 + 'contribution' => '', 142 + 'gifted' => "", 143 + 'not_yet' => "", 144 + 'valid_until' => '', 145 + 'was_valid_until' => '', 146 + ], 147 + ], 148 + ];
+78
resources/lang/kk-KZ/contest.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'header' => [ 8 + 'small' => '', 9 + 'large' => '', 10 + ], 11 + 12 + 'index' => [ 13 + 'nav_title' => '', 14 + ], 15 + 16 + 'voting' => [ 17 + 'login_required' => '', 18 + 'over' => '', 19 + 'show_voted_only' => '', 20 + 21 + 'best_of' => [ 22 + 'none_played' => "", 23 + ], 24 + 25 + 'button' => [ 26 + 'add' => '', 27 + 'remove' => '', 28 + 'used_up' => '', 29 + ], 30 + 31 + 'progress' => [ 32 + '_' => '', 33 + ], 34 + 35 + 'requirement' => [ 36 + 'playlist_beatmapsets' => [ 37 + 'incomplete_play' => '', 38 + ], 39 + ], 40 + ], 41 + 'entry' => [ 42 + '_' => '', 43 + 'login_required' => '', 44 + 'silenced_or_restricted' => '', 45 + 'preparation' => '', 46 + 'drop_here' => '', 47 + 'download' => '', 48 + 'wrong_type' => [ 49 + 'art' => '', 50 + 'beatmap' => '', 51 + 'music' => '', 52 + ], 53 + 'wrong_dimensions' => '', 54 + 'too_big' => '', 55 + ], 56 + 'beatmaps' => [ 57 + 'download' => '', 58 + ], 59 + 'vote' => [ 60 + 'list' => '', 61 + 'count' => '', 62 + 'points' => '', 63 + ], 64 + 'dates' => [ 65 + 'ended' => '', 66 + 'ended_no_date' => '', 67 + 68 + 'starts' => [ 69 + '_' => '', 70 + 'soon' => '', 71 + ], 72 + ], 73 + 'states' => [ 74 + 'entry' => '', 75 + 'voting' => '', 76 + 'results' => '', 77 + ], 78 + ];
+36
resources/lang/kk-KZ/errors.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'load_failed' => '', 8 + 'missing_route' => '', 9 + 'no_restricted_access' => '', 10 + 'supporter_only' => '', 11 + 'unknown' => '', 12 + 13 + 'codes' => [ 14 + 'http-401' => '', 15 + 'http-403' => '', 16 + 'http-404' => '', 17 + 'http-429' => '', 18 + ], 19 + 'account' => [ 20 + 'profile-order' => [ 21 + 'generic' => '', 22 + ], 23 + ], 24 + 'beatmaps' => [ 25 + 'invalid_mode' => '', 26 + 'standard_converts_only' => '', 27 + ], 28 + 'checkout' => [ 29 + 'generic' => '', 30 + ], 31 + 'search' => [ 32 + 'default' => '', 33 + 'invalid_cursor_exception' => '', 34 + 'operation_timeout_exception' => '', 35 + ], 36 + ];
+28
resources/lang/kk-KZ/events.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'achievement' => '', 8 + 'beatmap_playcount' => '', 9 + 'beatmapset_approve' => '', 10 + 'beatmapset_delete' => '', 11 + 'beatmapset_revive' => '', 12 + 'beatmapset_update' => '', 13 + 'beatmapset_upload' => '', 14 + 'empty' => "", 15 + 'rank' => '', 16 + 'rank_lost' => '', 17 + 'user_support_again' => '', 18 + 'user_support_first' => '', 19 + 'user_support_gift' => '', 20 + 'username_change' => '', 21 + 22 + 'beatmapset_status' => [ 23 + 'approved' => '', 24 + 'loved' => '', 25 + 'qualified' => '', 26 + 'ranked' => '', 27 + ], 28 + ];
+38
resources/lang/kk-KZ/follows.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'comment' => [ 8 + 'empty' => '', 9 + 'page_title' => '', 10 + 'title' => '', 11 + 12 + 'table' => [ 13 + 'latest_comment_empty' => '', 14 + 'latest_comment_value' => '', 15 + ], 16 + ], 17 + 18 + 'forum_topic' => [ 19 + 'title' => '', 20 + ], 21 + 22 + 'index' => [ 23 + 'title_compact' => '', 24 + ], 25 + 26 + 'mapping' => [ 27 + 'empty' => '', 28 + 'followers' => '', 29 + 'page_title' => '', 30 + 'title' => '', 31 + 'to_0' => '', 32 + 'to_1' => '', 33 + ], 34 + 35 + 'modding' => [ 36 + 'title' => '', 37 + ], 38 + ];
+378
resources/lang/kk-KZ/forum.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'pinned_topics' => '', 8 + 'slogan' => "", 9 + 'subforums' => '', 10 + 'title' => '', 11 + 12 + 'covers' => [ 13 + 'edit' => '', 14 + 15 + 'create' => [ 16 + '_' => '', 17 + 'button' => '', 18 + 'info' => '', 19 + ], 20 + 21 + 'destroy' => [ 22 + '_' => '', 23 + 'confirm' => '', 24 + ], 25 + ], 26 + 27 + 'forums' => [ 28 + 'forums' => '', 29 + 'latest_post' => '', 30 + 31 + 'index' => [ 32 + 'title' => '', 33 + ], 34 + 35 + 'topics' => [ 36 + 'empty' => '', 37 + ], 38 + ], 39 + 40 + 'mark_as_read' => [ 41 + 'forum' => '', 42 + 'forums' => '', 43 + 'busy' => '', 44 + ], 45 + 46 + 'post' => [ 47 + 'confirm_destroy' => '', 48 + 'confirm_restore' => '', 49 + 'edited' => '', 50 + 'posted_at' => '', 51 + 'posted_by_in' => '', 52 + 53 + 'actions' => [ 54 + 'destroy' => '', 55 + 'edit' => '', 56 + 'report' => '', 57 + 'restore' => '', 58 + ], 59 + 60 + 'create' => [ 61 + 'title' => [ 62 + 'reply' => '', 63 + ], 64 + ], 65 + 66 + 'info' => [ 67 + 'post_count' => '', 68 + 'topic_starter' => '', 69 + ], 70 + ], 71 + 72 + 'search' => [ 73 + 'go_to_post' => '', 74 + 'post_number_input' => '', 75 + 'total_posts' => '', 76 + ], 77 + 78 + 'topic' => [ 79 + 'confirm_destroy' => '', 80 + 'confirm_restore' => '', 81 + 'deleted' => '', 82 + 'go_to_latest' => '', 83 + 'has_replied' => '', 84 + 'in_forum' => '', 85 + 'latest_post' => '', 86 + 'latest_reply_by' => '', 87 + 'new_topic' => '', 88 + 'new_topic_login' => '', 89 + 'post_reply' => '', 90 + 'reply_box_placeholder' => '', 91 + 'reply_title_prefix' => '', 92 + 'started_by' => '', 93 + 'started_by_verbose' => '', 94 + 95 + 'actions' => [ 96 + 'destroy' => '', 97 + 'restore' => '', 98 + ], 99 + 100 + 'create' => [ 101 + 'close' => '', 102 + 'preview' => '', 103 + // TL note: this is used in the topic reply preview, when 104 + // the user goes back from previewing to editing the reply 105 + 'preview_hide' => '', 106 + 'submit' => '', 107 + 108 + 'necropost' => [ 109 + 'default' => '', 110 + 111 + 'new_topic' => [ 112 + '_' => "", 113 + 'create' => '', 114 + ], 115 + ], 116 + 117 + 'placeholder' => [ 118 + 'body' => '', 119 + 'title' => '', 120 + ], 121 + ], 122 + 123 + 'jump' => [ 124 + 'enter' => '', 125 + 'first' => '', 126 + 'last' => '', 127 + 'next' => '', 128 + 'previous' => '', 129 + ], 130 + 131 + 'logs' => [ 132 + '_' => '', 133 + 'button' => '', 134 + 135 + 'columns' => [ 136 + 'action' => '', 137 + 'date' => '', 138 + 'user' => '', 139 + ], 140 + 141 + 'data' => [ 142 + 'add_tag' => '', 143 + 'announcement' => '', 144 + 'edit_topic' => '', 145 + 'fork' => '', 146 + 'pin' => '', 147 + 'post_operation' => '', 148 + 'remove_tag' => '', 149 + 'source_forum_operation' => '', 150 + 'unpin' => '', 151 + ], 152 + 153 + 'no_results' => '', 154 + 155 + 'operations' => [ 156 + 'delete_post' => '', 157 + 'delete_topic' => '', 158 + 'edit_topic' => '', 159 + 'edit_poll' => '', 160 + 'fork' => '', 161 + 'issue_tag' => '', 162 + 'lock' => '', 163 + 'merge' => '', 164 + 'move' => '', 165 + 'pin' => '', 166 + 'post_edited' => '', 167 + 'restore_post' => '', 168 + 'restore_topic' => '', 169 + 'split_destination' => '', 170 + 'split_source' => '', 171 + 'topic_type' => '', 172 + 'topic_type_changed' => '', 173 + 'unlock' => '', 174 + 'unpin' => '', 175 + 'user_lock' => '', 176 + 'user_unlock' => '', 177 + ], 178 + ], 179 + 180 + 'post_edit' => [ 181 + 'cancel' => '', 182 + 'post' => '', 183 + ], 184 + ], 185 + 186 + 'topic_watches' => [ 187 + 'index' => [ 188 + 'title_compact' => '', 189 + 190 + 'box' => [ 191 + 'total' => '', 192 + 'unread' => '', 193 + ], 194 + 195 + 'info' => [ 196 + 'total' => '', 197 + 'unread' => '', 198 + ], 199 + ], 200 + 201 + 'topic_buttons' => [ 202 + 'remove' => [ 203 + 'confirmation' => '', 204 + 'title' => '', 205 + ], 206 + ], 207 + ], 208 + 209 + 'topics' => [ 210 + '_' => '', 211 + 212 + 'actions' => [ 213 + 'login_reply' => '', 214 + 'reply' => '', 215 + 'reply_with_quote' => '', 216 + 'search' => '', 217 + ], 218 + 219 + 'create' => [ 220 + 'create_poll' => '', 221 + 222 + 'preview' => '', 223 + 224 + 'create_poll_button' => [ 225 + 'add' => '', 226 + 'remove' => '', 227 + ], 228 + 229 + 'poll' => [ 230 + 'hide_results' => '', 231 + 'hide_results_info' => '', 232 + 'length' => '', 233 + 'length_days_suffix' => '', 234 + 'length_info' => '', 235 + 'max_options' => '', 236 + 'max_options_info' => '', 237 + 'options' => '', 238 + 'options_info' => '', 239 + 'title' => '', 240 + 'vote_change' => '', 241 + 'vote_change_info' => '', 242 + ], 243 + ], 244 + 245 + 'edit_title' => [ 246 + 'start' => '', 247 + ], 248 + 249 + 'index' => [ 250 + 'feature_votes' => '', 251 + 'replies' => '', 252 + 'views' => '', 253 + ], 254 + 255 + 'issue_tag_added' => [ 256 + 'to_0' => '', 257 + 'to_0_done' => '', 258 + 'to_1' => '', 259 + 'to_1_done' => '', 260 + ], 261 + 262 + 'issue_tag_assigned' => [ 263 + 'to_0' => '', 264 + 'to_0_done' => '', 265 + 'to_1' => '', 266 + 'to_1_done' => '', 267 + ], 268 + 269 + 'issue_tag_confirmed' => [ 270 + 'to_0' => '', 271 + 'to_0_done' => '', 272 + 'to_1' => '', 273 + 'to_1_done' => '', 274 + ], 275 + 276 + 'issue_tag_duplicate' => [ 277 + 'to_0' => '', 278 + 'to_0_done' => '', 279 + 'to_1' => '', 280 + 'to_1_done' => '', 281 + ], 282 + 283 + 'issue_tag_invalid' => [ 284 + 'to_0' => '', 285 + 'to_0_done' => '', 286 + 'to_1' => '', 287 + 'to_1_done' => '', 288 + ], 289 + 290 + 'issue_tag_resolved' => [ 291 + 'to_0' => '', 292 + 'to_0_done' => '', 293 + 'to_1' => '', 294 + 'to_1_done' => '', 295 + ], 296 + 297 + 'lock' => [ 298 + 'is_locked' => '', 299 + 'to_0' => '', 300 + 'to_0_confirm' => '', 301 + 'to_0_done' => '', 302 + 'to_1' => '', 303 + 'to_1_confirm' => '', 304 + 'to_1_done' => '', 305 + ], 306 + 307 + 'moderate_move' => [ 308 + 'title' => '', 309 + ], 310 + 311 + 'moderate_pin' => [ 312 + 'to_0' => '', 313 + 'to_0_confirm' => '', 314 + 'to_0_done' => '', 315 + 'to_1' => '', 316 + 'to_1_confirm' => '', 317 + 'to_1_done' => '', 318 + 'to_2' => '', 319 + 'to_2_confirm' => '', 320 + 'to_2_done' => '', 321 + ], 322 + 323 + 'moderate_toggle_deleted' => [ 324 + 'show' => '', 325 + 'hide' => '', 326 + ], 327 + 328 + 'show' => [ 329 + 'deleted-posts' => '', 330 + 'total_posts' => '', 331 + 332 + 'feature_vote' => [ 333 + 'current' => '', 334 + 'do' => '', 335 + 336 + 'info' => [ 337 + '_' => '', 338 + 'feature_request' => '', 339 + 'supporters' => '', 340 + ], 341 + 342 + 'user' => [ 343 + 'count' => '', 344 + 'current' => '', 345 + 'not_enough' => "", 346 + ], 347 + ], 348 + 349 + 'poll' => [ 350 + 'edit' => '', 351 + 'edit_warning' => '', 352 + 'vote' => '', 353 + 354 + 'button' => [ 355 + 'change_vote' => '', 356 + 'edit' => '', 357 + 'view_results' => '', 358 + 'vote' => '', 359 + ], 360 + 361 + 'detail' => [ 362 + 'end_time' => '', 363 + 'ended' => '', 364 + 'results_hidden' => '', 365 + 'total' => '', 366 + ], 367 + ], 368 + ], 369 + 370 + 'watch' => [ 371 + 'to_not_watching' => '', 372 + 'to_watching' => '', 373 + 'to_watching_mail' => '', 374 + 'tooltip_mail_disable' => '', 375 + 'tooltip_mail_enable' => '', 376 + ], 377 + ], 378 + ];
+15
resources/lang/kk-KZ/friends.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'title_compact' => '', 8 + 'too_many' => '', 9 + 10 + 'buttons' => [ 11 + 'add' => '', 12 + 'disabled' => '', 13 + 'remove' => '', 14 + ], 15 + ];
+6
resources/lang/kk-KZ/help.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [];
+147
resources/lang/kk-KZ/home.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'landing' => [ 8 + 'download' => '', 9 + 'online' => '', 10 + 'peak' => '', 11 + 'players' => '', 12 + 'title' => '', 13 + 'see_more_news' => '', 14 + 15 + 'slogan' => [ 16 + 'main' => '', 17 + 'sub' => '', 18 + ], 19 + ], 20 + 21 + 'search' => [ 22 + 'advanced_link' => '', 23 + 'button' => '', 24 + 'empty_result' => '', 25 + 'keyword_required' => '', 26 + 'placeholder' => '', 27 + 'title' => '', 28 + 29 + 'beatmapset' => [ 30 + 'login_required' => '', 31 + 'more' => '', 32 + 'more_simple' => '', 33 + 'title' => '', 34 + ], 35 + 36 + 'forum_post' => [ 37 + 'all' => '', 38 + 'link' => '', 39 + 'login_required' => '', 40 + 'more_simple' => '', 41 + 'title' => '', 42 + 43 + 'label' => [ 44 + 'forum' => '', 45 + 'forum_children' => '', 46 + 'include_deleted' => '', 47 + 'topic_id' => '', 48 + 'username' => '', 49 + ], 50 + ], 51 + 52 + 'mode' => [ 53 + 'all' => '', 54 + 'beatmapset' => '', 55 + 'forum_post' => '', 56 + 'user' => '', 57 + 'wiki_page' => '', 58 + ], 59 + 60 + 'user' => [ 61 + 'login_required' => '', 62 + 'more' => '', 63 + 'more_simple' => '', 64 + 'more_hidden' => '', 65 + 'title' => '', 66 + ], 67 + 68 + 'wiki_page' => [ 69 + 'link' => '', 70 + 'more_simple' => '', 71 + 'title' => '', 72 + ], 73 + ], 74 + 75 + 'download' => [ 76 + 'action' => '', 77 + 'action_lazer' => '', 78 + 'action_lazer_description' => '', 79 + 'action_lazer_info' => '', 80 + 'action_lazer_title' => '', 81 + 'action_title' => '', 82 + 'for_os' => '', 83 + 'lazer_note' => '', 84 + 'macos-fallback' => '', 85 + 'mirror' => '', 86 + 'or' => '', 87 + 'os_version_or_later' => '', 88 + 'other_os' => '', 89 + 'quick_start_guide' => '', 90 + 'tagline' => "", 91 + 'video-guide' => '', 92 + 93 + 'help' => [ 94 + '_' => '', 95 + 'help_forum_link' => '', 96 + 'support_button' => '', 97 + ], 98 + 99 + 'os' => [ 100 + 'windows' => '', 101 + 'macos' => '', 102 + 'linux' => '', 103 + ], 104 + 'steps' => [ 105 + 'register' => [ 106 + 'title' => '', 107 + 'description' => '', 108 + ], 109 + 'download' => [ 110 + 'title' => '', 111 + 'description' => '', 112 + ], 113 + 'beatmaps' => [ 114 + 'title' => '', 115 + 'description' => [ 116 + '_' => '', 117 + 'browse' => '', 118 + ], 119 + ], 120 + ], 121 + ], 122 + 123 + 'user' => [ 124 + 'title' => '', 125 + 'news' => [ 126 + 'title' => '', 127 + 'error' => '', 128 + ], 129 + 'header' => [ 130 + 'stats' => [ 131 + 'friends' => '', 132 + 'games' => '', 133 + 'online' => '', 134 + ], 135 + ], 136 + 'beatmaps' => [ 137 + 'new' => '', 138 + 'popular' => '', 139 + 'by_user' => '', 140 + ], 141 + 'buttons' => [ 142 + 'download' => '', 143 + 'support' => '', 144 + 'store' => '', 145 + ], 146 + ], 147 + ];
+207
resources/lang/kk-KZ/layout.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'audio' => [ 8 + 'autoplay' => '', 9 + ], 10 + 11 + 'defaults' => [ 12 + 'page_description' => '', 13 + ], 14 + 15 + 'header' => [ 16 + 'admin' => [ 17 + 'beatmapset' => '', 18 + 'beatmapset_covers' => '', 19 + 'contest' => '', 20 + 'contests' => '', 21 + 'root' => '', 22 + ], 23 + 24 + 'artists' => [ 25 + 'index' => '', 26 + ], 27 + 28 + 'beatmapsets' => [ 29 + 'show' => '', 30 + 'discussions' => '', 31 + ], 32 + 33 + 'changelog' => [ 34 + 'index' => '', 35 + ], 36 + 37 + 'help' => [ 38 + 'index' => '', 39 + 'sitemap' => '', 40 + ], 41 + 42 + 'store' => [ 43 + 'cart' => '', 44 + 'orders' => '', 45 + 'products' => '', 46 + ], 47 + 48 + 'tournaments' => [ 49 + 'index' => '', 50 + ], 51 + 52 + 'users' => [ 53 + 'modding' => '', 54 + 'playlists' => '', 55 + 'realtime' => '', 56 + 'show' => '', 57 + ], 58 + ], 59 + 60 + 'gallery' => [ 61 + 'close' => '', 62 + 'fullscreen' => '', 63 + 'zoom' => '', 64 + 'previous' => '', 65 + 'next' => '', 66 + ], 67 + 68 + 'menu' => [ 69 + 'beatmaps' => [ 70 + '_' => '', 71 + ], 72 + 'community' => [ 73 + '_' => '', 74 + 'dev' => '', 75 + ], 76 + 'help' => [ 77 + '_' => '', 78 + 'getAbuse' => '', 79 + 'getFaq' => '', 80 + 'getRules' => '', 81 + 'getSupport' => '', 82 + ], 83 + 'home' => [ 84 + '_' => '', 85 + 'team' => '', 86 + ], 87 + 'rankings' => [ 88 + '_' => '', 89 + 'kudosu' => '', 90 + ], 91 + 'store' => [ 92 + '_' => '', 93 + ], 94 + ], 95 + 96 + 'footer' => [ 97 + 'general' => [ 98 + '_' => '', 99 + 'home' => '', 100 + 'changelog-index' => '', 101 + 'beatmaps' => '', 102 + 'download' => '', 103 + ], 104 + 'help' => [ 105 + '_' => '', 106 + 'faq' => '', 107 + 'forum' => '', 108 + 'livestreams' => '', 109 + 'report' => '', 110 + 'wiki' => '', 111 + ], 112 + 'legal' => [ 113 + '_' => '', 114 + 'copyright' => '', 115 + 'privacy' => '', 116 + 'server_status' => '', 117 + 'source_code' => '', 118 + 'terms' => '', 119 + ], 120 + ], 121 + 122 + 'errors' => [ 123 + '400' => [ 124 + 'error' => '', 125 + 'description' => '', 126 + ], 127 + '404' => [ 128 + 'error' => '', 129 + 'description' => "", 130 + ], 131 + '403' => [ 132 + 'error' => "", 133 + 'description' => '', 134 + ], 135 + '401' => [ 136 + 'error' => "", 137 + 'description' => '', 138 + ], 139 + '405' => [ 140 + 'error' => '', 141 + 'description' => "", 142 + ], 143 + '422' => [ 144 + 'error' => '', 145 + 'description' => '', 146 + ], 147 + '429' => [ 148 + 'error' => '', 149 + 'description' => '', 150 + ], 151 + '500' => [ 152 + 'error' => '', 153 + 'description' => "", 154 + ], 155 + 'fatal' => [ 156 + 'error' => '', 157 + 'description' => "", 158 + ], 159 + '503' => [ 160 + 'error' => '', 161 + 'description' => "", 162 + 'link' => [ 163 + 'text' => '', 164 + 'href' => '', 165 + ], 166 + ], 167 + // used by sentry if it returns an error 168 + 'reference' => "", 169 + ], 170 + 171 + 'popup_login' => [ 172 + 'button' => '', 173 + 174 + 'login' => [ 175 + 'forgot' => "", 176 + 'password' => '', 177 + 'title' => '', 178 + 'username' => '', 179 + 180 + 'error' => [ 181 + 'email' => "", 182 + 'password' => '', 183 + ], 184 + ], 185 + 186 + 'register' => [ 187 + 'download' => '', 188 + 'info' => '', 189 + 'title' => "", 190 + ], 191 + ], 192 + 193 + 'popup_user' => [ 194 + 'links' => [ 195 + 'account-edit' => '', 196 + 'follows' => '', 197 + 'friends' => '', 198 + 'logout' => '', 199 + 'profile' => '', 200 + ], 201 + ], 202 + 203 + 'popup_search' => [ 204 + 'initial' => '', 205 + 'retry' => '', 206 + ], 207 + ];
+30
resources/lang/kk-KZ/legacy_api_key.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'new' => '', 8 + 'none' => '', 9 + 10 + 'docs' => [ 11 + '_' => '', 12 + 'github' => '', 13 + ], 14 + 15 + 'form' => [ 16 + 'create' => '', 17 + ], 18 + 19 + 'view' => [ 20 + 'hide' => '', 21 + 'show' => '', 22 + 'delete' => '', 23 + ], 24 + 25 + 'warning' => [ 26 + 'line1' => '', 27 + 'line2' => "", 28 + 'line3' => '', 29 + ], 30 + ];
+23
resources/lang/kk-KZ/legacy_irc_key.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'confirm_new' => '', 8 + 'new' => '', 9 + 'none' => '', 10 + 11 + 'form' => [ 12 + 'server_host' => '', 13 + 'server_port' => '', 14 + 'token' => '', 15 + 'username' => '', 16 + ], 17 + 18 + 'view' => [ 19 + 'hide' => '', 20 + 'show' => '', 21 + 'delete' => '', 22 + ], 23 + ];
+18
resources/lang/kk-KZ/livestreams.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'promote' => [ 8 + 'pin' => '', 9 + 'unpin' => "", 10 + ], 11 + 12 + 'top-headers' => [ 13 + 'headline' => '', 14 + 'description' => '', 15 + 16 + 'link' => '', 17 + ], 18 + ];
+111
resources/lang/kk-KZ/mail.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'beatmapset_update_notice' => [ 8 + 'new' => '', 9 + 'subject' => '', 10 + 'unwatch' => '', 11 + 'visit' => '', 12 + ], 13 + 14 + 'common' => [ 15 + 'closing' => '', 16 + 'hello' => '', 17 + 'report' => '', 18 + 'ignore' => '', 19 + ], 20 + 21 + 'donation_thanks' => [ 22 + 'benefit_more' => '', 23 + 'feedback' => "", 24 + 'keep_free' => '', 25 + 'keep_running' => '', 26 + 'subject' => '', 27 + 'translation' => '', 28 + 29 + 'benefit' => [ 30 + 'gift' => '', 31 + 'self' => '', 32 + ], 33 + 34 + 'support' => [ 35 + '_' => '', 36 + 'first' => '', 37 + 'repeat' => '', 38 + ], 39 + ], 40 + 41 + 'forum_new_reply' => [ 42 + 'new' => '', 43 + 'subject' => '', 44 + 'unwatch' => '', 45 + 'visit' => '', 46 + ], 47 + 48 + 'password_reset' => [ 49 + 'code' => '', 50 + 'requested' => '', 51 + 'subject' => '', 52 + ], 53 + 54 + 'store_payment_completed' => [ 55 + 'prepare_shipping' => '', 56 + 'processing' => '', 57 + 'questions' => "", 58 + 'shipping' => '', 59 + 'subject' => '', 60 + 'thank_you' => '', 61 + 'total' => '', 62 + ], 63 + 64 + 'supporter_gift' => [ 65 + 'anonymous_gift' => '', 66 + 'anonymous_gift_maybe_not' => '', 67 + 'duration' => '', 68 + 'features' => '', 69 + 'gifted' => '', 70 + 'gift_message' => '', 71 + 'subject' => '', 72 + ], 73 + 74 + 'user_email_updated' => [ 75 + 'changed_to' => '', 76 + 'check' => '', 77 + 'sent' => '', 78 + 'subject' => '', 79 + ], 80 + 81 + 'user_force_reactivation' => [ 82 + 'main' => '', 83 + 'perform_reset' => '', 84 + 'reason' => '', 85 + 'subject' => '', 86 + ], 87 + 88 + 'user_notification_digest' => [ 89 + 'new' => '', 90 + 'settings' => '', 91 + 'subject' => '', 92 + ], 93 + 94 + 'user_password_updated' => [ 95 + 'confirmation' => '', 96 + 'subject' => '', 97 + ], 98 + 99 + 'user_verification' => [ 100 + 'code' => '', 101 + 'code_hint' => '', 102 + 'link' => '', 103 + 'report' => '', 104 + 'subject' => '', 105 + 106 + 'action_from' => [ 107 + '_' => '', 108 + 'unknown_country' => '', 109 + ], 110 + ], 111 + ];
+61
resources/lang/kk-KZ/matches.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'match' => [ 8 + 'beatmap-deleted' => '', 9 + 'failed' => '', 10 + 'header' => '', 11 + 'in-progress' => '', 12 + 'in_progress_spinner_label' => '', 13 + 'loading-events' => '', 14 + 'winner' => '', 15 + 'winner_by' => '', 16 + 17 + 'events' => [ 18 + 'player-left' => '', 19 + 'player-joined' => '', 20 + 'player-kicked' => '', 21 + 'match-created' => '', 22 + 'match-disbanded' => '', 23 + 'host-changed' => '', 24 + 25 + 'player-left-no-user' => '', 26 + 'player-joined-no-user' => '', 27 + 'player-kicked-no-user' => '', 28 + 'match-created-no-user' => '', 29 + 'match-disbanded-no-user' => '', 30 + 'host-changed-no-user' => '', 31 + ], 32 + 33 + 'score' => [ 34 + 'stats' => [ 35 + 'accuracy' => '', 36 + 'combo' => '', 37 + 'score' => '', 38 + ], 39 + ], 40 + 41 + 'team-types' => [ 42 + 'head-to-head' => '', 43 + 'tag-coop' => '', 44 + 'team-vs' => '', 45 + 'tag-team-vs' => '', 46 + ], 47 + 48 + 'teams' => [ 49 + 'blue' => '', 50 + 'red' => '', 51 + ], 52 + ], 53 + 'game' => [ 54 + 'scoring-type' => [ 55 + 'score' => '', 56 + 'accuracy' => '', 57 + 'combo' => '', 58 + 'scorev2' => '', 59 + ], 60 + ], 61 + ];
+191
resources/lang/kk-KZ/model_validation.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'invalid' => '', 8 + 'not_negative' => '', 9 + 'required' => '', 10 + 'too_long' => '', 11 + 'url' => '', 12 + 'wrong_confirmation' => '', 13 + 14 + 'beatmapset_discussion' => [ 15 + 'beatmap_missing' => '', 16 + 'beatmapset_no_hype' => "", 17 + 'hype_requires_null_beatmap' => '', 18 + 'invalid_beatmap_id' => '', 19 + 'invalid_beatmapset_id' => '', 20 + 'locked' => '', 21 + 22 + 'attributes' => [ 23 + 'message_type' => '', 24 + 'timestamp' => '', 25 + ], 26 + 27 + 'hype' => [ 28 + 'discussion_locked' => "", 29 + 'guest' => '', 30 + 'hyped' => '', 31 + 'limit_exceeded' => '', 32 + 'not_hypeable' => '', 33 + 'owner' => '', 34 + ], 35 + 36 + 'timestamp' => [ 37 + 'exceeds_beatmapset_length' => '', 38 + 'negative' => "", 39 + ], 40 + ], 41 + 42 + 'beatmapset_discussion_post' => [ 43 + 'discussion_locked' => '', 44 + 'first_post' => '', 45 + 46 + 'attributes' => [ 47 + 'message' => '', 48 + ], 49 + ], 50 + 51 + 'comment' => [ 52 + 'deleted_parent' => '', 53 + 'top_only' => '', 54 + 55 + 'attributes' => [ 56 + 'message' => '', 57 + ], 58 + ], 59 + 60 + 'follow' => [ 61 + 'invalid' => '', 62 + ], 63 + 64 + 'forum' => [ 65 + 'feature_vote' => [ 66 + 'not_feature_topic' => '', 67 + 'not_enough_feature_votes' => '', 68 + ], 69 + 70 + 'poll_vote' => [ 71 + 'invalid' => '', 72 + ], 73 + 74 + 'post' => [ 75 + 'beatmapset_post_no_delete' => '', 76 + 'beatmapset_post_no_edit' => '', 77 + 'first_post_no_delete' => '', 78 + 'missing_topic' => '', 79 + 'only_quote' => '', 80 + 81 + 'attributes' => [ 82 + 'post_text' => '', 83 + ], 84 + ], 85 + 86 + 'topic' => [ 87 + 'attributes' => [ 88 + 'topic_title' => '', 89 + ], 90 + ], 91 + 92 + 'topic_poll' => [ 93 + 'duplicate_options' => '', 94 + 'grace_period_expired' => '', 95 + 'hiding_results_forever' => '', 96 + 'invalid_max_options' => '', 97 + 'minimum_one_selection' => '', 98 + 'minimum_two_options' => '', 99 + 'too_many_options' => '', 100 + 101 + 'attributes' => [ 102 + 'title' => '', 103 + ], 104 + ], 105 + 106 + 'topic_vote' => [ 107 + 'required' => '', 108 + 'too_many' => '', 109 + ], 110 + ], 111 + 112 + 'legacy_api_key' => [ 113 + 'exists' => '', 114 + 115 + 'attributes' => [ 116 + 'api_key' => '', 117 + 'app_name' => '', 118 + 'app_url' => '', 119 + ], 120 + ], 121 + 122 + 'oauth' => [ 123 + 'client' => [ 124 + 'too_many' => '', 125 + 'url' => '', 126 + 127 + 'attributes' => [ 128 + 'name' => '', 129 + 'redirect' => '', 130 + ], 131 + ], 132 + ], 133 + 134 + 'user' => [ 135 + 'contains_username' => '', 136 + 'email_already_used' => '', 137 + 'email_not_allowed' => '', 138 + 'invalid_country' => '', 139 + 'invalid_discord' => '', 140 + 'invalid_email' => "", 141 + 'invalid_twitter' => '', 142 + 'too_short' => '', 143 + 'unknown_duplicate' => '', 144 + 'username_available_in' => '', 145 + 'username_available_soon' => '', 146 + 'username_invalid_characters' => '', 147 + 'username_in_use' => '', 148 + 'username_locked' => '', // TODO: language for this should be slightly different. 149 + 'username_no_space_userscore_mix' => '', 150 + 'username_no_spaces' => "", 151 + 'username_not_allowed' => '', 152 + 'username_too_short' => '', 153 + 'username_too_long' => '', 154 + 'weak' => '', 155 + 'wrong_current_password' => '', 156 + 'wrong_email_confirmation' => '', 157 + 'wrong_password_confirmation' => '', 158 + 'too_long' => '', 159 + 160 + 'attributes' => [ 161 + 'username' => '', 162 + 'user_email' => '', 163 + 'password' => '', 164 + ], 165 + 166 + 'change_username' => [ 167 + 'restricted' => '', 168 + 'supporter_required' => [ 169 + '_' => '', 170 + 'link_text' => '', 171 + ], 172 + 'username_is_same' => '', 173 + ], 174 + ], 175 + 176 + 'user_report' => [ 177 + 'no_ranked_beatmapset' => '', 178 + 'not_in_channel' => '', 179 + 'reason_not_valid' => '', 180 + 'self' => "", 181 + ], 182 + 183 + 'store' => [ 184 + 'order_item' => [ 185 + 'attributes' => [ 186 + 'quantity' => '', 187 + 'cost' => '', 188 + ], 189 + ], 190 + ], 191 + ];
+15
resources/lang/kk-KZ/model_validation/fulfillments.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'username_change' => [ 8 + 'only_one' => '', 9 + 'insufficient_paid' => '', 10 + 'reverting_username_mismatch' => '', 11 + ], 12 + 'supporter_tag' => [ 13 + 'insufficient_paid' => '', 14 + ], 15 + ];
+37
resources/lang/kk-KZ/model_validation/payments.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'signature' => [ 8 + 'not_match' => '', 9 + ], 10 + 'notification_type' => '', 11 + 'order' => [ 12 + 'invalid' => '', 13 + 'items' => [ 14 + 'virtual_only' => '', 15 + ], 16 + 'status' => [ 17 + 'not_checkout' => '', 18 + 'not_paid' => '', 19 + ], 20 + ], 21 + 'param' => [ 22 + 'invalid' => '', 23 + ], 24 + 'paypal' => [ 25 + 'not_echeck' => '', 26 + ], 27 + 'purchase' => [ 28 + 'checkout' => [ 29 + 'amount' => '', 30 + 'currency' => '', 31 + ], 32 + ], 33 + 'order_number' => [ 34 + 'malformed' => '', 35 + 'user_id_mismatch' => '', 36 + ], 37 + ];
+11
resources/lang/kk-KZ/model_validation/store/product.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'insufficient_stock' => '', 8 + 'must_separate' => '', 9 + 'not_available' => '', 10 + 'too_many' => '', 11 + ];
+30
resources/lang/kk-KZ/multiplayer.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'empty' => [ 8 + '_' => '', 9 + 'playlists' => '', 10 + 'realtime' => '', 11 + ], 12 + 13 + 'room' => [ 14 + 'hosted_by' => '', 15 + 'invalid_password' => '', 16 + 'map_count' => '', 17 + 'player_count' => '', 18 + 'time_left' => '', 19 + 20 + 'errors' => [ 21 + 'duration_too_long' => '', 22 + ], 23 + 24 + 'status' => [ 25 + 'active' => '', 26 + 'ended' => '', 27 + 'soon' => '', 28 + ], 29 + ], 30 + ];
+48
resources/lang/kk-KZ/news.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'index' => [ 8 + 'title_page' => '', 9 + 10 + 'nav' => [ 11 + 'newer' => '', 12 + 'older' => '', 13 + ], 14 + 15 + 'title' => [ 16 + '_' => '', 17 + 'info' => '', 18 + ], 19 + ], 20 + 21 + 'show' => [ 22 + 'by' => '', 23 + 24 + 'nav' => [ 25 + 'newer' => '', 26 + 'older' => '', 27 + ], 28 + 29 + 'title' => [ 30 + '_' => '', 31 + 'info' => '', 32 + ], 33 + ], 34 + 35 + 'sidebar' => [ 36 + 'archive' => '', 37 + ], 38 + 39 + 'store' => [ 40 + 'button' => '', 41 + 'ok' => '', 42 + ], 43 + 44 + 'update' => [ 45 + 'button' => '', 46 + 'ok' => '', 47 + ], 48 + ];
+252
resources/lang/kk-KZ/notifications.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'all_read' => '', 8 + 'delete' => '', 9 + 'loading' => '', 10 + 'mark_read' => '', 11 + 'none' => '', 12 + 'see_all' => '', 13 + 'see_channel' => '', 14 + 'verifying' => '', 15 + 16 + 'action_type' => [ 17 + '_' => '', 18 + 'beatmapset' => '', 19 + 'build' => '', 20 + 'channel' => '', 21 + 'forum_topic' => '', 22 + 'news_post' => '', 23 + 'user' => '', 24 + ], 25 + 26 + 'filters' => [ 27 + '_' => '', 28 + 'user' => '', 29 + 'beatmapset' => '', 30 + 'forum_topic' => '', 31 + 'news_post' => '', 32 + 'build' => '', 33 + 'channel' => '', 34 + ], 35 + 36 + 'item' => [ 37 + 'beatmapset' => [ 38 + '_' => '', 39 + 40 + 'beatmap_owner_change' => [ 41 + '_' => '', 42 + 'beatmap_owner_change' => '', 43 + 'beatmap_owner_change_compact' => '', 44 + ], 45 + 46 + 'beatmapset_discussion' => [ 47 + '_' => '', 48 + 'beatmapset_discussion_lock' => '', 49 + 'beatmapset_discussion_lock_compact' => '', 50 + 'beatmapset_discussion_post_new' => '', 51 + 'beatmapset_discussion_post_new_empty' => '', 52 + 'beatmapset_discussion_post_new_compact' => '', 53 + 'beatmapset_discussion_post_new_compact_empty' => '', 54 + 'beatmapset_discussion_review_new' => '', 55 + 'beatmapset_discussion_review_new_compact' => '', 56 + 'beatmapset_discussion_unlock' => '', 57 + 'beatmapset_discussion_unlock_compact' => '', 58 + ], 59 + 60 + 'beatmapset_problem' => [ 61 + '_' => '', 62 + 'beatmapset_discussion_qualified_problem' => '', 63 + 'beatmapset_discussion_qualified_problem_empty' => '', 64 + 'beatmapset_discussion_qualified_problem_compact' => '', 65 + 'beatmapset_discussion_qualified_problem_compact_empty' => '', 66 + ], 67 + 68 + 'beatmapset_state' => [ 69 + '_' => '', 70 + 'beatmapset_disqualify' => '', 71 + 'beatmapset_disqualify_compact' => '', 72 + 'beatmapset_love' => '', 73 + 'beatmapset_love_compact' => '', 74 + 'beatmapset_nominate' => '', 75 + 'beatmapset_nominate_compact' => '', 76 + 'beatmapset_qualify' => '', 77 + 'beatmapset_qualify_compact' => '', 78 + 'beatmapset_rank' => '', 79 + 'beatmapset_rank_compact' => '', 80 + 'beatmapset_remove_from_loved' => '', 81 + 'beatmapset_remove_from_loved_compact' => '', 82 + 'beatmapset_reset_nominations' => '', 83 + 'beatmapset_reset_nominations_compact' => '', 84 + ], 85 + 86 + 'comment' => [ 87 + '_' => '', 88 + 89 + 'comment_new' => '', 90 + 'comment_new_compact' => '', 91 + 'comment_reply' => '', 92 + 'comment_reply_compact' => '', 93 + ], 94 + ], 95 + 96 + 'channel' => [ 97 + '_' => '', 98 + 99 + 'announcement' => [ 100 + '_' => '', 101 + 102 + 'announce' => [ 103 + 'channel_announcement' => '', 104 + 'channel_announcement_compact' => '', 105 + 'channel_announcement_group' => '', 106 + ], 107 + ], 108 + 109 + 'channel' => [ 110 + '_' => '', 111 + 112 + 'pm' => [ 113 + 'channel_message' => '', 114 + 'channel_message_compact' => '', 115 + 'channel_message_group' => '', 116 + ], 117 + ], 118 + ], 119 + 120 + 'build' => [ 121 + '_' => '', 122 + 123 + 'comment' => [ 124 + '_' => '', 125 + 126 + 'comment_new' => '', 127 + 'comment_new_compact' => '', 128 + 'comment_reply' => '', 129 + 'comment_reply_compact' => '', 130 + ], 131 + ], 132 + 133 + 'news_post' => [ 134 + '_' => '', 135 + 136 + 'comment' => [ 137 + '_' => '', 138 + 139 + 'comment_new' => '', 140 + 'comment_new_compact' => '', 141 + 'comment_reply' => '', 142 + 'comment_reply_compact' => '', 143 + ], 144 + ], 145 + 146 + 'forum_topic' => [ 147 + '_' => '', 148 + 149 + 'forum_topic_reply' => [ 150 + '_' => '', 151 + 'forum_topic_reply' => '', 152 + 'forum_topic_reply_compact' => '', 153 + ], 154 + ], 155 + 156 + 'user' => [ 157 + 'user_beatmapset_new' => [ 158 + '_' => '', 159 + 160 + 'user_beatmapset_new' => '', 161 + 'user_beatmapset_new_compact' => '', 162 + 'user_beatmapset_new_group' => '', 163 + 164 + 'user_beatmapset_revive' => '', 165 + 'user_beatmapset_revive_compact' => '', 166 + ], 167 + ], 168 + 169 + 'user_achievement' => [ 170 + '_' => '', 171 + 172 + 'user_achievement_unlock' => [ 173 + '_' => '', 174 + 'user_achievement_unlock' => '', 175 + 'user_achievement_unlock_compact' => '', 176 + 'user_achievement_unlock_group' => '', 177 + ], 178 + ], 179 + ], 180 + 181 + 'mail' => [ 182 + 'beatmapset' => [ 183 + 'beatmap_owner_change' => [ 184 + 'beatmap_owner_change' => '', 185 + ], 186 + 187 + 'beatmapset_discussion' => [ 188 + 'beatmapset_discussion_lock' => '', 189 + 'beatmapset_discussion_post_new' => '', 190 + 'beatmapset_discussion_unlock' => '', 191 + ], 192 + 193 + 'beatmapset_problem' => [ 194 + 'beatmapset_discussion_qualified_problem' => '', 195 + ], 196 + 197 + 'beatmapset_state' => [ 198 + 'beatmapset_disqualify' => '', 199 + 'beatmapset_love' => '', 200 + 'beatmapset_nominate' => '', 201 + 'beatmapset_qualify' => '', 202 + 'beatmapset_rank' => '', 203 + 'beatmapset_remove_from_loved' => '', 204 + 'beatmapset_reset_nominations' => '', 205 + ], 206 + 207 + 'comment' => [ 208 + 'comment_new' => '', 209 + ], 210 + ], 211 + 212 + 'channel' => [ 213 + 'announcement' => [ 214 + 'announce' => '', 215 + ], 216 + 217 + 'channel' => [ 218 + 'pm' => '', 219 + ], 220 + ], 221 + 222 + 'build' => [ 223 + 'comment' => [ 224 + 'comment_new' => '', 225 + ], 226 + ], 227 + 228 + 'news_post' => [ 229 + 'comment' => [ 230 + 'comment_new' => '', 231 + ], 232 + ], 233 + 234 + 'forum_topic' => [ 235 + 'forum_topic_reply' => [ 236 + 'forum_topic_reply' => '', 237 + ], 238 + ], 239 + 240 + 'user' => [ 241 + 'user_achievement_unlock' => [ 242 + 'user_achievement_unlock' => '', 243 + 'user_achievement_unlock_self' => '', 244 + ], 245 + 246 + 'user_beatmapset_new' => [ 247 + 'user_beatmapset_new' => '', 248 + 'user_beatmapset_revive' => '', 249 + ], 250 + ], 251 + ], 252 + ];
+61
resources/lang/kk-KZ/oauth.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'cancel' => '', 8 + 9 + 'authorise' => [ 10 + 'request' => '', 11 + 'scopes_title' => '', 12 + 'title' => '', 13 + ], 14 + 15 + 'authorized_clients' => [ 16 + 'confirm_revoke' => '', 17 + 'scopes_title' => '', 18 + 'owned_by' => '', 19 + 'none' => '', 20 + 21 + 'revoked' => [ 22 + 'false' => '', 23 + 'true' => '', 24 + ], 25 + ], 26 + 27 + 'client' => [ 28 + 'id' => '', 29 + 'name' => '', 30 + 'redirect' => '', 31 + 'reset' => '', 32 + 'reset_failed' => '', 33 + 'secret' => '', 34 + 35 + 'secret_visible' => [ 36 + 'false' => '', 37 + 'true' => '', 38 + ], 39 + ], 40 + 41 + 'new_client' => [ 42 + 'header' => '', 43 + 'register' => '', 44 + 'terms_of_use' => [ 45 + '_' => '', 46 + 'link' => '', 47 + ], 48 + ], 49 + 50 + 'own_clients' => [ 51 + 'confirm_delete' => '', 52 + 'confirm_reset' => '', 53 + 'new' => '', 54 + 'none' => '', 55 + 56 + 'revoked' => [ 57 + 'false' => '', 58 + 'true' => '', 59 + ], 60 + ], 61 + ];
+134
resources/lang/kk-KZ/page_title.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'admin' => [ 8 + '_' => '', 9 + ], 10 + 'error' => [ 11 + 'error' => [ 12 + '400' => '', 13 + '404' => '', 14 + '403' => '', 15 + '401' => '', 16 + '401-verification' => '', 17 + '405' => '', 18 + '422' => '', 19 + '429' => '', 20 + '500' => '', 21 + '503' => '', 22 + ], 23 + ], 24 + 'forum' => [ 25 + '_' => '', 26 + 'topic_logs_controller' => [ 27 + 'index' => '', 28 + ], 29 + ], 30 + 'main' => [ 31 + 'account_controller' => [ 32 + 'verify_link' => '', 33 + ], 34 + 'artists_controller' => [ 35 + '_' => '', 36 + ], 37 + 'beatmap_discussion_posts_controller' => [ 38 + '_' => '', 39 + ], 40 + 'beatmap_discussions_controller' => [ 41 + '_' => '', 42 + ], 43 + 'beatmap_packs_controller' => [ 44 + '_' => '', 45 + ], 46 + 'beatmapset_discussion_votes_controller' => [ 47 + '_' => '', 48 + ], 49 + 'beatmapset_events_controller' => [ 50 + '_' => '', 51 + ], 52 + 'beatmapsets_controller' => [ 53 + 'discussion' => '', 54 + 'index' => '', 55 + 'show' => '', 56 + ], 57 + 'changelog_controller' => [ 58 + '_' => '', 59 + ], 60 + 'chat_controller' => [ 61 + '_' => '', 62 + ], 63 + 'comments_controller' => [ 64 + '_' => '', 65 + ], 66 + 'contests_controller' => [ 67 + '_' => '', 68 + ], 69 + 'groups_controller' => [ 70 + 'show' => '', 71 + ], 72 + 'home_controller' => [ 73 + 'get_download' => '', 74 + 'index' => '', 75 + 'search' => '', 76 + 'support_the_game' => '', 77 + 'testflight' => '', 78 + ], 79 + 'legal_controller' => [ 80 + '_' => '', 81 + ], 82 + 'livestreams_controller' => [ 83 + '_' => '', 84 + ], 85 + 'matches_controller' => [ 86 + '_' => '', 87 + ], 88 + 'news_controller' => [ 89 + '_' => '', 90 + ], 91 + 'notifications_controller' => [ 92 + '_' => '', 93 + ], 94 + 'password_reset_controller' => [ 95 + '_' => '', 96 + ], 97 + 'ranking_controller' => [ 98 + '_' => '', 99 + ], 100 + 'scores_controller' => [ 101 + '_' => '', 102 + ], 103 + 'seasons_controller' => [ 104 + '_' => '', 105 + ], 106 + 'tournaments_controller' => [ 107 + '_' => '', 108 + ], 109 + 'users_controller' => [ 110 + '_' => '', 111 + 'create' => '', 112 + 'disabled' => '', 113 + ], 114 + 'wiki_controller' => [ 115 + '_' => '', 116 + ], 117 + ], 118 + 'passport' => [ 119 + 'authorization_controller' => [ 120 + '_' => '', 121 + ], 122 + ], 123 + 'store' => [ 124 + '_' => '', 125 + ], 126 + 'users' => [ 127 + 'modding_history_controller' => [ 128 + '_' => '', 129 + ], 130 + 'multiplayer_controller' => [ 131 + '_' => '', 132 + ], 133 + ], 134 + ];
+45
resources/lang/kk-KZ/password_reset.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'button' => [ 8 + 'cancel' => '', 9 + 'resend' => '', 10 + 'set' => '', 11 + 'start' => '', 12 + ], 13 + 14 + 'error' => [ 15 + 'contact_support' => '', 16 + 'expired' => '', 17 + 'invalid' => '', 18 + 'is_privileged' => '', 19 + 'missing_key' => '', 20 + 'too_many_tries' => '', 21 + 'user_not_found' => '', 22 + 'wrong_key' => '', 23 + ], 24 + 25 + 'notice' => [ 26 + 'sent' => '', 27 + 'saved' => '', 28 + ], 29 + 30 + 'started' => [ 31 + 'password' => '', 32 + 'password_confirmation' => '', 33 + 'title' => '', 34 + 'verification_key' => '', 35 + ], 36 + 37 + 'starting' => [ 38 + 'username' => '', 39 + 40 + 'support' => [ 41 + '_' => '', 42 + 'button' => '', 43 + ], 44 + ], 45 + ];
+13
resources/lang/kk-KZ/paypal/errors.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'instrument_declined' => '', 8 + 'invalid_resource_id' => '', 9 + 'invalid_token' => '', 10 + 'old_format' => '', 11 + 'resource_not_found' => '', 12 + 'unknown' => "", 13 + ];
+21
resources/lang/kk-KZ/quick_search.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'mode' => [ 8 + 'beatmapset' => '', 9 + 'forum_post' => '', 10 + 'other' => '', 11 + 'user' => '', 12 + 'wiki_page' => '', 13 + ], 14 + 15 + 'result' => [ 16 + 'empty' => '', 17 + 'empty_for' => '', 18 + 'more' => '', 19 + 'title' => '', 20 + ], 21 + ];
+64
resources/lang/kk-KZ/rankings.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'countries' => [ 8 + 'all' => '', 9 + 'title' => '', 10 + ], 11 + 12 + 'filter' => [ 13 + 'title' => '', 14 + 15 + 'variant' => [ 16 + 'title' => '', 17 + ], 18 + ], 19 + 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 26 + 'type' => [ 27 + 'charts' => '', 28 + 'country' => '', 29 + 'kudosu' => '', 30 + 'multiplayer' => '', 31 + 'performance' => '', 32 + 'score' => '', 33 + 'seasons' => '', 34 + ], 35 + 36 + 'seasons' => [ 37 + 'empty' => '', 38 + 'ongoing' => '', 39 + 'room_count' => '', 40 + 'url' => '', 41 + ], 42 + 43 + 'spotlight' => [ 44 + 'end_date' => '', 45 + 'map_count' => '', 46 + 'participants' => '', 47 + 'start_date' => '', 48 + ], 49 + 50 + 'stat' => [ 51 + 'accuracy' => '', 52 + 'active_users' => '', 53 + 'country' => '', 54 + 'play_count' => '', 55 + 'performance' => '', 56 + 'total_score' => '', 57 + 'ranked_score' => '', 58 + 'average_score' => '', 59 + 'average_performance' => '', 60 + 'ss' => '', 61 + 's' => '', 62 + 'a' => '', 63 + ], 64 + ];
+36
resources/lang/kk-KZ/report.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'beatmapset' => [ 8 + 'button' => '', 9 + 'title' => '', 10 + ], 11 + 12 + 'beatmapset_discussion_post' => [ 13 + 'button' => '', 14 + 'title' => '', 15 + ], 16 + 17 + 'comment' => [ 18 + 'button' => '', 19 + 'title' => '', 20 + ], 21 + 22 + 'forum_post' => [ 23 + 'button' => '', 24 + 'title' => '', 25 + ], 26 + 27 + 'scores' => [ 28 + 'button' => '', 29 + 'title' => '', 30 + ], 31 + 32 + 'user' => [ 33 + 'button' => '', 34 + 'title' => '', 35 + ], 36 + ];
+30
resources/lang/kk-KZ/scores.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'show' => [ 8 + 'title' => '', 9 + 10 + 'beatmap' => [ 11 + 'by' => '', 12 + ], 13 + 14 + 'player' => [ 15 + 'by' => '', 16 + 'submitted_on' => '', 17 + 18 + 'rank' => [ 19 + 'country' => '', 20 + 'global' => '', 21 + ], 22 + ], 23 + ], 24 + 25 + 'status' => [ 26 + 'non_best' => '', 27 + 'non_passing' => '', 28 + 'processing' => '', 29 + ], 30 + ];
+12
resources/lang/kk-KZ/sessions.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'create' => [ 8 + 'download' => '', 9 + 'label' => '', 10 + 'title' => '', 11 + ], 12 + ];
+44
resources/lang/kk-KZ/sort.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + '_' => '', 8 + 9 + 'all' => '', 10 + 'friends' => '', 11 + 'last_visit' => '', 12 + 'new' => '', 13 + 'old' => '', 14 + 'rank' => '', 15 + 'top' => '', 16 + 'username' => '', 17 + 18 + 'artist_tracks' => [ 19 + 'album' => '', 20 + 'artist' => '', 21 + 'bpm' => '', 22 + 'genre' => '', 23 + 'length' => '', 24 + 'relevance' => '', 25 + 'title' => '', 26 + 'update' => '', 27 + ], 28 + 29 + 'forum_posts' => [ 30 + 'created' => '', 31 + 'relevance' => '', 32 + ], 33 + 34 + 'forum_topics' => [ 35 + 'created' => '', 36 + 'feature_votes' => '', 37 + 'new' => '', 38 + ], 39 + 40 + 'users' => [ 41 + 'relevance' => '', 42 + 'username' => '', 43 + ], 44 + ];
+150
resources/lang/kk-KZ/store.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'cart' => [ 8 + 'checkout' => '', 9 + 'info' => '', 10 + 'more_goodies' => '', 11 + 'shipping_fees' => '', 12 + 'title' => '', 13 + 'total' => '', 14 + 15 + 'errors_no_checkout' => [ 16 + 'line_1' => '', 17 + 'line_2' => '', 18 + ], 19 + 20 + 'empty' => [ 21 + 'text' => '', 22 + 'return_link' => [ 23 + '_' => '', 24 + 'link_text' => '', 25 + ], 26 + ], 27 + ], 28 + 29 + 'checkout' => [ 30 + 'cart_problems' => '', 31 + 'cart_problems_edit' => '', 32 + 'declined' => '', 33 + 'delayed_shipping' => '', 34 + 'hide_from_activity' => '', 35 + 'old_cart' => '', 36 + 'pay' => '', 37 + 'title_compact' => '', 38 + 39 + 'has_pending' => [ 40 + '_' => '', 41 + 'link_text' => '', 42 + ], 43 + 44 + 'pending_checkout' => [ 45 + 'line_1' => '', 46 + 'line_2' => '', 47 + ], 48 + ], 49 + 50 + 'discount' => '', 51 + 52 + 'invoice' => [ 53 + 'echeck_delay' => '', 54 + 'hide_from_activity' => '', 55 + 'title_compact' => '', 56 + 57 + 'status' => [ 58 + 'processing' => [ 59 + 'title' => '', 60 + 'line_1' => '', 61 + 'line_2' => [ 62 + '_' => '', 63 + 'link_text' => '', 64 + ], 65 + ], 66 + ], 67 + ], 68 + 69 + 'order' => [ 70 + 'cancel' => '', 71 + 'cancel_confirm' => '', 72 + 'cancel_not_allowed' => '', 73 + 'invoice' => '', 74 + 'no_orders' => '', 75 + 'paid_on' => '', 76 + 'resume' => '', 77 + 'shopify_expired' => '', 78 + 79 + 'item' => [ 80 + 'quantity' => '', 81 + 82 + 'display_name' => [ 83 + 'supporter_tag' => '', 84 + ], 85 + 86 + 'subtext' => [ 87 + 'supporter_tag' => '', 88 + ], 89 + ], 90 + 91 + 'not_modifiable_exception' => [ 92 + 'cancelled' => '', 93 + 'checkout' => '', // checkout and processing should have the same message. 94 + 'default' => '', 95 + 'delivered' => '', 96 + 'paid' => '', 97 + 'processing' => '', 98 + 'shipped' => '', 99 + ], 100 + 101 + 'status' => [ 102 + 'cancelled' => '', 103 + 'checkout' => '', 104 + 'delivered' => '', 105 + 'paid' => '', 106 + 'processing' => '', 107 + 'shipped' => '', 108 + ], 109 + ], 110 + 111 + 'product' => [ 112 + 'name' => '', 113 + 114 + 'stock' => [ 115 + 'out' => '', 116 + 'out_with_alternative' => '', 117 + ], 118 + 119 + 'add_to_cart' => '', 120 + 'notify' => '', 121 + 122 + 'notification_success' => '', 123 + 'notification_remove_text' => '', 124 + 125 + 'notification_in_stock' => '', 126 + ], 127 + 128 + 'supporter_tag' => [ 129 + 'gift' => '', 130 + 'gift_message' => '', 131 + 132 + 'require_login' => [ 133 + '_' => '', 134 + 'link_text' => '', 135 + ], 136 + ], 137 + 138 + 'username_change' => [ 139 + 'check' => '', 140 + 'checking' => '', 141 + 'require_login' => [ 142 + '_' => '', 143 + 'link_text' => '', 144 + ], 145 + ], 146 + 147 + 'xsolla' => [ 148 + 'distributor' => '', 149 + ], 150 + ];
+13
resources/lang/kk-KZ/supporter_tag.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'months' => '', 8 + 9 + 'user_search' => [ 10 + 'searching' => '', 11 + 'not_found' => "", 12 + ], 13 + ];
+52
resources/lang/kk-KZ/tournament.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'index' => [ 8 + 'none_running' => '', 9 + 'registration_period' => '', 10 + 11 + 'header' => [ 12 + 'title' => '', 13 + ], 14 + 15 + 'item' => [ 16 + 'registered' => '', 17 + ], 18 + 19 + 'state' => [ 20 + 'current' => '', 21 + 'previous' => '', 22 + ], 23 + ], 24 + 25 + 'show' => [ 26 + 'banner' => '', 27 + 'entered' => '', 28 + 'info_page' => '', 29 + 'login_to_register' => '', 30 + 'not_yet_entered' => '', 31 + 'rank_too_low' => '', 32 + 'registration_ends' => '', 33 + 34 + 'button' => [ 35 + 'cancel' => '', 36 + 'register' => '', 37 + ], 38 + 39 + 'period' => [ 40 + 'end' => '', 41 + 'start' => '', 42 + ], 43 + 44 + 'state' => [ 45 + 'before_registration' => '', 46 + 'ended' => '', 47 + 'registration_closed' => '', 48 + 'running' => '', 49 + ], 50 + ], 51 + 'tournament_period' => '', 52 + ];
+30
resources/lang/kk-KZ/user_verification.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'box' => [ 8 + 'sent' => '', 9 + 'title' => '', 10 + 'verifying' => '', 11 + 'issuing' => '', 12 + 13 + 'info' => [ 14 + 'check_spam' => "", 15 + 'recover' => "", 16 + 'recover_link' => '', 17 + 'reissue' => '', 18 + 'reissue_link' => '', 19 + 'logout_link' => '', 20 + ], 21 + ], 22 + 23 + 'errors' => [ 24 + 'expired' => '', 25 + 'incorrect_key' => '', 26 + 'retries_exceeded' => '', 27 + 'reissued' => '', 28 + 'unknown' => '', 29 + ], 30 + ];
+486
resources/lang/kk-KZ/users.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'deleted' => '', 8 + 9 + 'beatmapset_activities' => [ 10 + 'title' => "", 11 + 'title_compact' => '', 12 + 13 + 'discussions' => [ 14 + 'title_recent' => '', 15 + ], 16 + 17 + 'events' => [ 18 + 'title_recent' => '', 19 + ], 20 + 21 + 'posts' => [ 22 + 'title_recent' => '', 23 + ], 24 + 25 + 'votes_received' => [ 26 + 'title_most' => '', 27 + ], 28 + 29 + 'votes_made' => [ 30 + 'title_most' => '', 31 + ], 32 + ], 33 + 34 + 'blocks' => [ 35 + 'banner_text' => '', 36 + 'comment_text' => '', 37 + 'blocked_count' => '', 38 + 'hide_profile' => '', 39 + 'hide_comment' => '', 40 + 'forum_post_text' => '', 41 + 'not_blocked' => '', 42 + 'show_profile' => '', 43 + 'show_comment' => '', 44 + 'too_many' => '', 45 + 'button' => [ 46 + 'block' => '', 47 + 'unblock' => '', 48 + ], 49 + ], 50 + 51 + 'card' => [ 52 + 'gift_supporter' => '', 53 + 'loading' => '', 54 + 'send_message' => '', 55 + ], 56 + 57 + 'create' => [ 58 + 'form' => [ 59 + 'password' => '', 60 + 'password_confirmation' => '', 61 + 'submit' => '', 62 + 'user_email' => '', 63 + 'user_email_confirmation' => '', 64 + 'username' => '', 65 + 66 + 'tos_notice' => [ 67 + '_' => '', 68 + 'link' => '', 69 + ], 70 + ], 71 + ], 72 + 73 + 'disabled' => [ 74 + 'title' => '', 75 + 'warning' => "", 76 + 77 + 'if_mistake' => [ 78 + '_' => '', 79 + 'email' => '', 80 + ], 81 + 82 + 'reasons' => [ 83 + 'compromised' => '', 84 + 'opening' => '', 85 + 86 + 'tos' => [ 87 + '_' => '', 88 + 'community_rules' => '', 89 + 'tos' => '', 90 + ], 91 + ], 92 + ], 93 + 94 + 'filtering' => [ 95 + 'by_game_mode' => '', 96 + ], 97 + 98 + 'force_reactivation' => [ 99 + 'reason' => [ 100 + 'inactive_different_country' => "", 101 + ], 102 + ], 103 + 104 + 'login' => [ 105 + '_' => '', 106 + 'button' => '', 107 + 'button_posting' => '', 108 + 'email_login_disabled' => '', 109 + 'failed' => '', 110 + 'forgot' => '', 111 + 'info' => '', 112 + 'invalid_captcha' => '', 113 + 'locked_ip' => '', 114 + 'password' => '', 115 + 'register' => "", 116 + 'remember' => '', 117 + 'title' => '', 118 + 'username' => '', 119 + 120 + 'beta' => [ 121 + 'main' => '', 122 + 'small' => '', 123 + ], 124 + ], 125 + 126 + 'posts' => [ 127 + 'title' => '', 128 + ], 129 + 130 + 'anonymous' => [ 131 + 'login_link' => '', 132 + 'login_text' => '', 133 + 'username' => '', 134 + 'error' => '', 135 + ], 136 + 'logout_confirm' => '', 137 + 'report' => [ 138 + 'button_text' => '', 139 + 'comments' => '', 140 + 'placeholder' => '', 141 + 'reason' => '', 142 + 'thanks' => '', 143 + 'title' => '', 144 + 145 + 'actions' => [ 146 + 'send' => '', 147 + 'cancel' => '', 148 + ], 149 + 150 + 'options' => [ 151 + 'cheating' => '', 152 + 'multiple_accounts' => '', 153 + 'insults' => '', 154 + 'spam' => '', 155 + 'unwanted_content' => '', 156 + 'nonsense' => '', 157 + 'other' => '', 158 + ], 159 + ], 160 + 'restricted_banner' => [ 161 + 'title' => '', 162 + 'message' => '', 163 + 'message_link' => '', 164 + ], 165 + 'show' => [ 166 + 'age' => '', 167 + 'change_avatar' => '', 168 + 'first_members' => '', 169 + 'is_developer' => '', 170 + 'is_supporter' => '', 171 + 'joined_at' => '', 172 + 'lastvisit' => '', 173 + 'lastvisit_online' => '', 174 + 'missingtext' => '', 175 + 'origin_country' => '', 176 + 'previous_usernames' => '', 177 + 'plays_with' => '', 178 + 'title' => "", 179 + 180 + 'comments_count' => [ 181 + '_' => '', 182 + 'count' => '', 183 + ], 184 + 'cover' => [ 185 + 'to_0' => '', 186 + 'to_1' => '', 187 + ], 188 + 'edit' => [ 189 + 'cover' => [ 190 + 'button' => '', 191 + 'defaults_info' => '', 192 + 'upload' => [ 193 + 'broken_file' => '', 194 + 'button' => '', 195 + 'dropzone' => '', 196 + 'dropzone_info' => '', 197 + 'size_info' => '', 198 + 'too_large' => '', 199 + 'unsupported_format' => '', 200 + 201 + 'restriction_info' => [ 202 + '_' => '', 203 + 'link' => '', 204 + ], 205 + ], 206 + ], 207 + 208 + 'default_playmode' => [ 209 + 'is_default_tooltip' => '', 210 + 'set' => '', 211 + ], 212 + ], 213 + 214 + 'extra' => [ 215 + 'none' => '', 216 + 'unranked' => '', 217 + 218 + 'achievements' => [ 219 + 'achieved-on' => '', 220 + 'locked' => '', 221 + 'title' => '', 222 + ], 223 + 'beatmaps' => [ 224 + 'by_artist' => '', 225 + 'title' => '', 226 + 227 + 'favourite' => [ 228 + 'title' => '', 229 + ], 230 + 'graveyard' => [ 231 + 'title' => '', 232 + ], 233 + 'guest' => [ 234 + 'title' => '', 235 + ], 236 + 'loved' => [ 237 + 'title' => '', 238 + ], 239 + 'nominated' => [ 240 + 'title' => '', 241 + ], 242 + 'pending' => [ 243 + 'title' => '', 244 + ], 245 + 'ranked' => [ 246 + 'title' => '', 247 + ], 248 + ], 249 + 'discussions' => [ 250 + 'title' => '', 251 + 'title_longer' => '', 252 + 'show_more' => '', 253 + ], 254 + 'events' => [ 255 + 'title' => '', 256 + 'title_longer' => '', 257 + 'show_more' => '', 258 + ], 259 + 'historical' => [ 260 + 'title' => '', 261 + 262 + 'monthly_playcounts' => [ 263 + 'title' => '', 264 + 'count_label' => '', 265 + ], 266 + 'most_played' => [ 267 + 'count' => '', 268 + 'title' => '', 269 + ], 270 + 'recent_plays' => [ 271 + 'accuracy' => '', 272 + 'title' => '', 273 + ], 274 + 'replays_watched_counts' => [ 275 + 'title' => '', 276 + 'count_label' => '', 277 + ], 278 + ], 279 + 'kudosu' => [ 280 + 'recent_entries' => '', 281 + 'title' => '', 282 + 'total' => '', 283 + 284 + 'entry' => [ 285 + 'amount' => '', 286 + 'empty' => "", 287 + 288 + 'beatmap_discussion' => [ 289 + 'allow_kudosu' => [ 290 + 'give' => '', 291 + ], 292 + 293 + 'deny_kudosu' => [ 294 + 'reset' => '', 295 + ], 296 + 297 + 'delete' => [ 298 + 'reset' => '', 299 + ], 300 + 301 + 'restore' => [ 302 + 'give' => '', 303 + ], 304 + 305 + 'vote' => [ 306 + 'give' => '', 307 + 'reset' => '', 308 + ], 309 + 310 + 'recalculate' => [ 311 + 'give' => '', 312 + 'reset' => '', 313 + ], 314 + ], 315 + 316 + 'forum_post' => [ 317 + 'give' => '', 318 + 'reset' => '', 319 + 'revoke' => '', 320 + ], 321 + ], 322 + 323 + 'total_info' => [ 324 + '_' => '', 325 + 'link' => '', 326 + ], 327 + ], 328 + 'me' => [ 329 + 'title' => '', 330 + ], 331 + 'medals' => [ 332 + 'empty' => "", 333 + 'recent' => '', 334 + 'title' => '', 335 + ], 336 + 'playlists' => [ 337 + 'title' => '', 338 + ], 339 + 'posts' => [ 340 + 'title' => '', 341 + 'title_longer' => '', 342 + 'show_more' => '', 343 + ], 344 + 'recent_activity' => [ 345 + 'title' => '', 346 + ], 347 + 'realtime' => [ 348 + 'title' => '', 349 + ], 350 + 'top_ranks' => [ 351 + 'download_replay' => '', 352 + 'not_ranked' => '', 353 + 'pp_weight' => '', 354 + 'view_details' => '', 355 + 'title' => '', 356 + 357 + 'best' => [ 358 + 'title' => '', 359 + ], 360 + 'first' => [ 361 + 'title' => '', 362 + ], 363 + 'pin' => [ 364 + 'to_0' => '', 365 + 'to_0_done' => '', 366 + 'to_1' => '', 367 + 'to_1_done' => '', 368 + ], 369 + 'pinned' => [ 370 + 'title' => '', 371 + ], 372 + ], 373 + 'votes' => [ 374 + 'given' => '', 375 + 'received' => '', 376 + 'title' => '', 377 + 'title_longer' => '', 378 + 'vote_count' => '', 379 + ], 380 + 'account_standing' => [ 381 + 'title' => '', 382 + 'bad_standing' => "", 383 + 'remaining_silence' => '', 384 + 385 + 'recent_infringements' => [ 386 + 'title' => '', 387 + 'date' => '', 388 + 'action' => '', 389 + 'length' => '', 390 + 'length_permanent' => '', 391 + 'description' => '', 392 + 'actor' => '', 393 + 394 + 'actions' => [ 395 + 'restriction' => '', 396 + 'silence' => '', 397 + 'tournament_ban' => '', 398 + 'note' => '', 399 + ], 400 + ], 401 + ], 402 + ], 403 + 404 + 'info' => [ 405 + 'discord' => '', 406 + 'interests' => '', 407 + 'location' => '', 408 + 'occupation' => '', 409 + 'twitter' => '', 410 + 'website' => '', 411 + ], 412 + 'not_found' => [ 413 + 'reason_1' => '', 414 + 'reason_2' => '', 415 + 'reason_3' => '', 416 + 'reason_header' => '', 417 + 'title' => '', 418 + ], 419 + 'page' => [ 420 + 'button' => '', 421 + 'description' => '', 422 + 'edit_big' => '', 423 + 'placeholder' => '', 424 + 425 + 'restriction_info' => [ 426 + '_' => '', 427 + 'link' => '', 428 + ], 429 + ], 430 + 'post_count' => [ 431 + '_' => '', 432 + 'count' => '', 433 + ], 434 + 'rank' => [ 435 + 'country' => '', 436 + 'country_simple' => '', 437 + 'global' => '', 438 + 'global_simple' => '', 439 + 'highest' => '', 440 + ], 441 + 'stats' => [ 442 + 'hit_accuracy' => '', 443 + 'level' => '', 444 + 'level_progress' => '', 445 + 'maximum_combo' => '', 446 + 'medals' => '', 447 + 'play_count' => '', 448 + 'play_time' => '', 449 + 'ranked_score' => '', 450 + 'replays_watched_by_others' => '', 451 + 'score_ranks' => '', 452 + 'total_hits' => '', 453 + 'total_score' => '', 454 + // modding stats 455 + 'graveyard_beatmapset_count' => '', 456 + 'loved_beatmapset_count' => '', 457 + 'pending_beatmapset_count' => '', 458 + 'ranked_beatmapset_count' => '', 459 + ], 460 + ], 461 + 462 + 'silenced_banner' => [ 463 + 'title' => '', 464 + 'message' => '', 465 + ], 466 + 467 + 'status' => [ 468 + 'all' => '', 469 + 'online' => '', 470 + 'offline' => '', 471 + ], 472 + 'store' => [ 473 + 'from_client' => '', 474 + 'from_web' => '', 475 + 'saved' => '', 476 + ], 477 + 'verify' => [ 478 + 'title' => '', 479 + ], 480 + 481 + 'view_mode' => [ 482 + 'brick' => '', 483 + 'card' => '', 484 + 'list' => '', 485 + ], 486 + ];
+9
resources/lang/kk-KZ/validation.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'mixture' => '', 8 + 'required' => '', 9 + ];
+30
resources/lang/kk-KZ/wiki.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + return [ 7 + 'show' => [ 8 + 'fallback_translation' => '', 9 + 'incomplete_or_outdated' => '', 10 + 'missing' => '', 11 + 'missing_title' => '', 12 + 'missing_translation' => '', 13 + 'needs_cleanup_or_rewrite' => '', 14 + 'search' => '', 15 + 'stub' => '', 16 + 'toc' => '', 17 + 18 + 'edit' => [ 19 + 'link' => '', 20 + 'refresh' => '', 21 + ], 22 + 23 + 'translation' => [ 24 + 'legal' => '', 25 + 'outdated' => '', 26 + 27 + 'default' => '', 28 + ], 29 + ], 30 + ];
+1
resources/lang/ko/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '점수 소유자만 점수를 고정할 수 있습니다.', 175 176 'too_many' => '너무 많은 점수를 고정했습니다.', 176 177 ],
-9
resources/lang/ko/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '이전 포럼 PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited개의 미확인 메시지', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '새 비트맵',
+7
resources/lang/ko/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => '스포트라이트', 22 28 'country' => '국가별', 29 + 'kudosu' => '', 23 30 'multiplayer' => '멀티플레이어', 24 31 'performance' => '퍼포먼스', 25 32 'score' => '점수',
+1
resources/lang/lt/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Tik rezultato savininkas gali prisegti rezultatą.', 175 176 'too_many' => 'Prisegta perdaug rezultatų.', 176 177 ],
-9
resources/lang/lt/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Senojo Forumo Pranešimas', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited neperskaityta žinutė|:count_delimited neperskaitytų žinučių', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Naujas bitmapas',
+7
resources/lang/lt/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'pasižymėje', 22 28 'country' => 'Šalimis', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'žaidimas tinkle', 24 31 'performance' => 'pp', 25 32 'score' => 'Taškai',
+1
resources/lang/lv-LV/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Rezultātu var piespraust tikai rezultāta īpašnieks.', 175 176 'too_many' => 'Piesprausti pārāk daudz rezultāti.', 176 177 ],
-9
resources/lang/lv-LV/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => '', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '',
+7
resources/lang/lv-LV/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Uzmanības centrā', 22 28 'country' => 'Valsts', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'Daudzspēlētāju režīms', 24 31 'performance' => 'Veiktspēja', 25 32 'score' => 'Punktu skaits',
+1
resources/lang/ms-MY/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '', 175 176 'too_many' => '', 176 177 ],
-9
resources/lang/ms-MY/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => '', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Beatmap baharu',
+7
resources/lang/ms-MY/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'sorotan', 22 28 'country' => 'negara', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'pemainan beramai', 24 31 'performance' => 'pencapaian', 25 32 'score' => 'markah',
+1
resources/lang/nl/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Enkel de eigenaar van de score kan deze vastzetten.', 175 176 'too_many' => 'Te veel scores vastgezet.', 176 177 ],
-9
resources/lang/nl/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Ouder Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited ongelezen bericht|:count_delimited berichten', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nieuwe beatmap',
+7
resources/lang/nl/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'in de schijnwerpers', 22 28 'country' => 'landelijk', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multiplayer', 24 31 'performance' => 'prestatie', 25 32 'score' => 'score',
+1
resources/lang/no/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Kun resultateieren kan festeresultat.', 175 176 'too_many' => 'Festet for mange resultater.', 176 177 ],
-9
resources/lang/no/notifications.php
··· 154 154 ], 155 155 ], 156 156 157 - 'legacy_pm' => [ 158 - '_' => 'Eldre Forum PM', 159 - 160 - 'legacy_pm' => [ 161 - '_' => '', 162 - 'legacy_pm' => ':count_delimited ulest melding.|:count_delimited uleste meldinger.', 163 - ], 164 - ], 165 - 166 157 'user' => [ 167 158 'user_beatmapset_new' => [ 168 159 '_' => 'Nytt beatmap',
+7
resources/lang/no/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Rampelyset', 22 28 'country' => 'Land', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'flerspiller', 24 31 'performance' => 'Prestasjon', 25 32 'score' => 'Poengsum',
+2 -2
resources/lang/pl/artist.php
··· 4 4 // See the LICENCE file in the repository root for full licence text. 5 5 6 6 return [ 7 - 'page_description' => 'Wyróżnieni artyści osu!', 7 + 'page_description' => 'Wyróżnieni wykonawcy osu!', 8 8 'title' => 'Wyróżnieni artyści', 9 9 10 10 'admin' => [ ··· 18 18 ], 19 19 20 20 'index' => [ 21 - 'description' => 'Wyróżnieni artyści to osoby z którymi współpracujemy, by zapewnić społeczności osu! oryginalną muzykę - część artystów stworzyła utwory wyłączne dla naszej gry! Zarówno oni sami, jak i ich utwory, zostali starannie wybrani przez członków zespołu osu!, głównie za ich odlotowość oraz łatwość w tworzeniu beatmap.<br><br>Wszystkie utwory w tej sekcji występują w formie plików o rozszerzeniu .osz z odpowiednio ustawionym rytmem. Utwory są oficjalnie licencjonowane dla osu! i rzeczy z nim powiązanych.', 21 + 'description' => 'Wyróżnieni wykonawcy to osoby z którymi współpracujemy, by zapewnić społeczności osu! oryginalną muzykę - część artystów stworzyła utwory wyłączne dla naszej gry! Zarówno oni sami, jak i ich utwory, zostali starannie wybrani przez członków zespołu osu!, głównie za ich odlotowość oraz łatwość w tworzeniu beatmap.<br><br>Wszystkie utwory w tej sekcji występują w formie plików o rozszerzeniu .osz z odpowiednio ustawionym rytmem. Utwory są oficjalnie licencjonowane dla osu! i rzeczy z nim powiązanych.', 22 22 ], 23 23 24 24 'links' => [
+1
resources/lang/pl/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Nie możesz przypiąć czyjegoś wyniku.', 175 176 'too_many' => 'Przypięto zbyt wiele wyników.', 176 177 ],
+1 -1
resources/lang/pl/chat.php
··· 8 8 'talking_in' => 'rozmowa na kanale :channel', 9 9 'talking_with' => 'rozmowa z użytkownikiem :name', 10 10 'title_compact' => 'czat', 11 - 'unread_messages' => 'nieprzeczytane wiadomości', 11 + 'unread_messages' => 'nieodczytane wiadomości', 12 12 13 13 'cannot_send' => [ 14 14 'channel' => 'W tej chwili nie możesz wysyłać wiadomości na ten kanał.',
-9
resources/lang/pl/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Skrzynka odbiorcza starego forum', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited nieprzeczytana wiadomość|:count_delimited nieprzeczytane wiadomości|:count_delimited nieprzeczytanych wiadomości', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nowa beatmapa',
+7
resources/lang/pl/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'wyróżnionych', 22 28 'country' => 'krajowy', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'wieloosobowy', 24 31 'performance' => 'globalny', 25 32 'score' => 'punktowy',
+1
resources/lang/pt-br/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Somente o proprietário da pontuação pode fixar sua pontuação.', 175 176 'too_many' => 'Muitas pontuações fixadas.', 176 177 ],
-9
resources/lang/pt-br/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Mensagens Privadas do Fórum Legado', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited mensagem não lida|:count_delimited mensagens não lidas', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Novo beatmap',
+7
resources/lang/pt-br/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Destaques', 22 28 'country' => 'país', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multijogador', 24 31 'performance' => 'desempenho', 25 32 'score' => 'pontuação',
+1
resources/lang/pt/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Só o dono da pontuação é que a pode fixar.', 175 176 'too_many' => 'Afixaste demasiadas pontuações.', 176 177 ],
+3 -3
resources/lang/pt/legacy_irc_key.php
··· 4 4 // See the LICENCE file in the repository root for full licence text. 5 5 6 6 return [ 7 - 'confirm_new' => '', 8 - 'new' => '', 9 - 'none' => '', 7 + 'confirm_new' => 'Criar nova palavra-passe de IRC?', 8 + 'new' => 'Nova palavra-passe de IRC legado', 9 + 'none' => 'A palavra-passe de IRC não foi definida.', 10 10 11 11 'form' => [ 12 12 'server_host' => 'servidor',
-9
resources/lang/pt/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Fórum de legado de mensagens privadas', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited mensagem não lida.|:count_delimited mensagens não lidas', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Novo beatmap',
+7
resources/lang/pt/rankings.php
··· 18 18 ], 19 19 ], 20 20 21 + 'kudosu' => [ 22 + 'total' => '', 23 + 'available' => '', 24 + 'used' => '', 25 + ], 26 + 21 27 'type' => [ 22 28 'charts' => 'Em destaque', 23 29 'country' => 'País', 30 + 'kudosu' => '', 24 31 'multiplayer' => 'multijogador', 25 32 'performance' => 'Desempenho', 26 33 'score' => 'Pontuação',
+1
resources/lang/ro/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Numai creatorul scorului poate fixa acest scor.', 175 176 'too_many' => 'Ai fixat prea multe scoruri.', 176 177 ],
+1 -1
resources/lang/ro/beatmap_discussions.php
··· 67 67 68 68 'reply' => [ 69 69 'open' => [ 70 - 'guest' => 'Conectează-te pentru a răspunde', 70 + 'guest' => 'Autentifică-te pentru a răspunde', 71 71 'user' => 'Răspunde', 72 72 ], 73 73 ],
+1 -1
resources/lang/ro/beatmappacks.php
··· 44 44 45 45 'require_login' => [ 46 46 '_' => 'Trebuie să fii :link pentru a descărca', 47 - 'link_text' => 'conectat', 47 + 'link_text' => 'autentificat', 48 48 ], 49 49 ];
+10 -10
resources/lang/ro/beatmaps.php
··· 26 26 'message_type_select' => 'Selectează tipul comentariului', 27 27 'reply_notice' => 'Apasă enter pentru a răspunde.', 28 28 'reply_placeholder' => 'Scrie-ți răspunsul aici', 29 - 'require-login' => 'Te rugăm să te conectezi pentru a posta sau a răspunde', 29 + 'require-login' => 'Te rugăm să te autentifici pentru a posta sau a răspunde', 30 30 'resolved' => 'Rezolvat', 31 31 'restore' => 'restabilește', 32 32 'show_deleted' => 'Arată șterse', ··· 158 158 ], 159 159 160 160 'hype' => [ 161 - 'button' => '\'Hype\' acest beatmap!', 162 - 'button_done' => 'Deja Hyped!', 163 - 'confirm' => "Ești sigur? Acest lucru îți va folosi unul din restul tău de :n 'hype' rămași și nu poate fi anulat.", 164 - 'explanation' => '\'Hype\' acest beatmap pentru a-l face mai vizibil pentru nominalizare și clasament!', 165 - 'explanation_guest' => 'Conectează-te și \'hype\' acest beatmap pentru a-l face mai vizibil pentru nominalizare și clasament!', 166 - 'new_time' => "O să primești alt 'hype' pe :new_time.", 167 - 'remaining' => 'Mai ai :remaining \'hype\' rămași.', 161 + 'button' => 'Acordă hype acestui beatmap!', 162 + 'button_done' => 'Hype deja acordat!', 163 + 'confirm' => "Ești sigur? Acest lucru îți va folosi unul din cele :n hype rămase și nu poate fi anulat.", 164 + 'explanation' => 'Acordă un hype acestui beatmap pentru a-l face mai vizibil pentru nominalizare și clasament!', 165 + 'explanation_guest' => 'Autentifică-te și acordă un hype acestui beatmap pentru a-l face mai vizibil pentru nominalizare și clasament!', 166 + 'new_time' => "Vei primi un alt hype pe :new_time.", 167 + 'remaining' => 'Mai ai :remaining hype rămași.', 168 168 'required_text' => 'Hype: :current/:required', 169 - 'section_title' => 'Trenul Hype', 169 + 'section_title' => 'Trenul de Hype', 170 170 'title' => 'Hype', 171 171 ], 172 172 ··· 191 191 'nominate' => 'Nominalizează', 192 192 'nominate_confirm' => 'Nominalizezi acest beatmap?', 193 193 'nominated_by' => 'nominalizat de :users', 194 - 'not_enough_hype' => "Nu este suficient hype.", 194 + 'not_enough_hype' => "Nu există suficient hype.", 195 195 'remove_from_loved' => 'Șterge din Iubit', 196 196 'remove_from_loved_prompt' => 'Motivul pentru ștergere din Iubit:', 197 197 'required_text' => 'Nominalizări: :current/:required',
+3 -3
resources/lang/ro/beatmapsets.php
··· 102 102 ], 103 103 104 104 'hype' => [ 105 - 'action' => 'Hype această mapă dacă ți-a plăcut să o joci, astfel încât să progreseze la stadiul de <strong>Clasat</strong>.', 105 + 'action' => 'Acordă un hype acestui beatmap dacă ți-a plăcut să îl joci pentru a îl ajuta să progreseze la stadiul de <strong>Clasat</strong>.', 106 106 107 107 'current' => [ 108 - '_' => 'Această mapă este în prezent :status.', 108 + '_' => 'Acest beatmap este în prezent :status.', 109 109 110 110 'status' => [ 111 111 'pending' => 'în așteptare', ··· 178 178 179 179 'no_scores' => [ 180 180 'country' => 'Nimeni din țara ta nu a stabilit un scor pe acest beatmap încă!', 181 - 'friend' => 'Nimeni din prietenii tăi nu a stabilit un scor pe acest beatmap încă!', 181 + 'friend' => 'Niciunul dintre prietenii tăi nu a stabilit un scor pe acest beatmap încă!', 182 182 'global' => 'Niciun scor încă. Poate ar trebui să încerci să obții câteva?', 183 183 'loading' => 'Se încarcă scorurile...', 184 184 'unranked' => 'Beatmap neclasificat.',
+1 -1
resources/lang/ro/common.php
··· 153 153 ], 154 154 155 155 'title' => [ 156 - 'notice' => 'Notificare', 156 + 'notice' => 'Observație', 157 157 ], 158 158 159 159 'wrong_user' => [
+4 -4
resources/lang/ro/model_validation.php
··· 13 13 14 14 'beatmapset_discussion' => [ 15 15 'beatmap_missing' => 'Marcajul de timp este specificat dar beatmap-ul lipsește.', 16 - 'beatmapset_no_hype' => "Acest beatmap nu poate fi hyped.", 17 - 'hype_requires_null_beatmap' => 'Hype trebuie să fie făcut în secțiunea General (toate dificultățile).', 16 + 'beatmapset_no_hype' => "Nu poți acorda hype acestui beatmap.", 17 + 'hype_requires_null_beatmap' => 'Hype-ul trebuie să fie acordat în secțiunea General (toate dificultățile).', 18 18 'invalid_beatmap_id' => 'Dificultatea specificată nu este validă.', 19 19 'invalid_beatmapset_id' => 'Beatmap-ul specificat nu este valid.', 20 20 'locked' => 'Discuția este închisă.', ··· 25 25 ], 26 26 27 27 'hype' => [ 28 - 'discussion_locked' => "Acest beatmap este momentan blocat pentru discuții și nu poate fi hyped", 28 + 'discussion_locked' => "Acest beatmap este momentan blocat pentru discuții și hype-ul nu poate fi acordat", 29 29 'guest' => 'Trebuie să fii autentificat pentru a acorda un hype.', 30 30 'hyped' => 'Deja ai acordat un hype acestui beatmap.', 31 31 'limit_exceeded' => 'Ți-ai folosit deja tot hype-ul.', 32 - 'not_hypeable' => 'Acest beatmap nu poate fi hyped', 32 + 'not_hypeable' => 'Nu poți acorda hype acestui beatmap', 33 33 'owner' => 'Nu ii poți acorda un hype propriului tău beatmap.', 34 34 ], 35 35
-9
resources/lang/ro/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'PM vechi forum', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => 'un mesaj necitit|:count_delimited mesaje necitite|:count_delimited de mesaje necitite', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Beatmap nou',
+7
resources/lang/ro/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'promovări', 22 28 'country' => 'pe țară', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'multiplayer', 24 31 'performance' => 'performanță', 25 32 'score' => 'scor',
+1 -1
resources/lang/ro/users.php
··· 49 49 ], 50 50 51 51 'card' => [ 52 - 'gift_supporter' => '', 52 + 'gift_supporter' => 'Oferă status de suporter osu! cadou', 53 53 'loading' => 'Se încarcă...', 54 54 'send_message' => 'trimite mesaj', 55 55 ],
+1
resources/lang/ru/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Можно закреплять лишь только свои рекорды.', 175 176 'too_many' => 'Закреплено слишком много рекордов.', 176 177 ],
-9
resources/lang/ru/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Старая система ЛС', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited непрочитанное сообщение|:count_delimited непрочитанных сообщения|:count_delimited непрочитанных сообщений', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Новая карта',
+7
resources/lang/ru/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'по чартам', 22 28 'country' => 'по странам', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'в мультиплеере', 24 31 'performance' => 'по производительности', 25 32 'score' => 'по очкам',
+1
resources/lang/si-LK/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '', 175 176 'too_many' => '', 176 177 ],
-9
resources/lang/si-LK/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => '', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '',
+7
resources/lang/si-LK/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => '', 22 28 'country' => '', 29 + 'kudosu' => '', 23 30 'multiplayer' => '', 24 31 'performance' => '', 25 32 'score' => '',
+1
resources/lang/sk/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Skóre môže pripnúť iba pôvodný hráč.', 175 176 'too_many' => 'Už bolo pripnuté maximum skóre.', 176 177 ],
-9
resources/lang/sk/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => '', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '',
+7
resources/lang/sk/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Výbery', 22 28 'country' => 'Krajina', 29 + 'kudosu' => '', 23 30 'multiplayer' => '', 24 31 'performance' => 'Výkon', 25 32 'score' => 'Skóre',
+1
resources/lang/sl/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Samo lastnik rezultata lahko pripne rezultat.', 175 176 'too_many' => 'Pripeto je preveč rezultatov.', 176 177 ],
-9
resources/lang/sl/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Stari forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited neprebrano sporočilo|:count_delimited neprebranih sporočil', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Nova beatmapa',
+7
resources/lang/sl/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'spotlights', 22 28 'country' => 'država', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'večigralski način', 24 31 'performance' => 'uspešnost', 25 32 'score' => 'rezultat',
+1
resources/lang/sr/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Само власник овог резултата може пиновати резултат.', 175 176 'too_many' => 'Пиновали сте превише резултата.', 176 177 ],
-9
resources/lang/sr/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Директна порука на старом форуму', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited непрочитана порука|:count_delimited непрочитане поруке', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Нова мапа',
+7
resources/lang/sr/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'колекције', 22 28 'country' => 'држава', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'мултиплејер', 24 31 'performance' => 'перформансе', 25 32 'score' => 'резултат',
+1
resources/lang/sv/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Endast resultatägaren kan fästa resultat.', 175 176 'too_many' => 'Fäst för många resultat.', 176 177 ],
-9
resources/lang/sv/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Forumets äldre PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited oläst meddelande|:count_delimited olästa meddelanden', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Ny beatmap',
+7
resources/lang/sv/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'i rampljuset', 22 28 'country' => 'land', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'flerspelarläge', 24 31 'performance' => 'prestation', 25 32 'score' => 'poäng',
+1
resources/lang/tg-TJ/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '', 175 176 'too_many' => '', 176 177 ],
-9
resources/lang/tg-TJ/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => '', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '',
+7
resources/lang/tg-TJ/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => '', 22 28 'country' => '', 29 + 'kudosu' => '', 23 30 'multiplayer' => '', 24 31 'performance' => '', 25 32 'score' => '',
+6 -6
resources/lang/th/accounts.php
··· 53 53 ], 54 54 55 55 'notifications' => [ 56 - 'beatmapset_discussion_qualified_problem' => 'ได้รับการแจ้งเตือนสำหรับปัญหาใหม่เกี่ยวกับบีตแม็ปที่ผ่านการรับรองของโหมดต่อไปนี้', 57 - 'beatmapset_disqualify' => 'ได้รับการแจ้งเตือนเมื่อบีตแม็ปในโหมดที่ท่านเลือกถูกตัดสิทธิ์', 56 + 'beatmapset_discussion_qualified_problem' => 'ได้รับการแจ้งเตือนเกียวกับปัญหาของบีทแมพที่ผ่านการรับรองกับโหมดต่อไปนี้', 57 + 'beatmapset_disqualify' => 'ได้รับการแจ้งเตือนเมื่อบีทแมพในโหมดที่ท่านเลือกถูกตัดสิทธิ์', 58 58 'comment_reply' => 'รับการแจ้งเตือนสำหรับการตอบกลับความคิดเห็นของคุณ', 59 59 'title' => 'การแจ้งเตือน', 60 60 'topic_auto_subscribe' => 'เปิดการแจ้งเตือนอัตโนมัติในกระทู้ที่คุณสร้างขึ้น', ··· 62 62 'options' => [ 63 63 '_' => 'วิธีการรับการแจ้งเตือน', 64 64 'beatmap_owner_change' => 'ระดับความยากของแขก', 65 - 'beatmapset:modding' => 'การวิจารณ์บีตแม็ป', 65 + 'beatmapset:modding' => 'การวิจารณ์บีทแมพ', 66 66 'channel_message' => 'ข้อความส่วนตัว', 67 67 'comment_new' => 'ความคิดเห็นใหม่', 68 68 'forum_topic_reply' => 'ข้อความตอบกลับในกระทู้', 69 69 'mail' => 'อีเมล', 70 - 'mapping' => 'ผู้ทำบีตแม็ป', 70 + 'mapping' => 'ผู้ทำบีทแมพ', 71 71 'push' => 'ส่งการแจ้งเตือน', 72 72 'user_achievement_unlock' => 'ผู้เล่นได้ปลดล็อกเหรียญตรา', 73 73 ], ··· 80 80 ], 81 81 82 82 'options' => [ 83 - 'beatmapset_show_nsfw' => 'ซ่อนคำเตือนเกี่ยวกับเนื้อหาที่ล่อแหลมในบีตแม็ป', 84 - 'beatmapset_title_show_original' => 'แสดงข้อมูลของบีตแม็ปในภาษาต้นฉบับ', 83 + 'beatmapset_show_nsfw' => 'ซ่อนคำเตือนเกี่ยวกับเนื้อหาที่ล่อแหลมในบีทแมพ', 84 + 'beatmapset_title_show_original' => 'แสดงข้อมูลของ บีทแมพ ในภาษาดั้งเดิม', 85 85 'title' => 'ตัวเลือก', 86 86 87 87 'beatmapset_download' => [
+3 -3
resources/lang/th/artist.php
··· 12 12 ], 13 13 14 14 'beatmaps' => [ 15 - '_' => 'บีตแม็ป', 15 + '_' => 'บีทแมพ', 16 16 'download' => 'ดาวน์โหลดตัวอย่างบีตแม็ป', 17 - 'download-na' => 'ตัวอย่าง Beatmap นี้ยังไม่สามารถให้ใช้งานได้', 17 + 'download-na' => 'ตัวอย่างบีทแมพนี้ยังไม่สามารถให้ใช้งานได้', 18 18 ], 19 19 20 20 'index' => [ ··· 22 22 ], 23 23 24 24 'links' => [ 25 - 'beatmaps' => 'osu! บีตแม็ป', 25 + 'beatmaps' => 'osu! บีทแมพ', 26 26 'osu' => 'โปรไฟล์ osu!', 27 27 'site' => 'เว็บไซต์อย่างเป็นทางการ', 28 28 ],
+7 -6
resources/lang/th/authorization.php
··· 19 19 'nominate' => [ 20 20 'exhausted' => 'คุณถึงขีดจำกัดของการเสนอชื่อแล้วสำหรับวันนี้ โปรดลองอีกครั้งในวันพรุ่งนี้', 21 21 'incorrect_state' => 'เกิดข้อผิดพลาดในการดำเนินการ ลองรีเฟรชหน้านี้ดู', 22 - 'owner' => "ไม่สามารถเสนอชื่อบีตแม็ปของตัวเองได้", 23 - 'set_metadata' => 'คุณต้องตั้งค่าหมวดหมู่เพลงและภาษาก่อนเสนอชื่อบีตแม็ป', 22 + 'owner' => "ไม่สามารถเสนอชื่อบีทแมพของตัวเองได้", 23 + 'set_metadata' => 'คุณต้องตั้งค่าหมวดหมู่เพลงและภาษาก่อนเสนอชื่อบีทแมพ', 24 24 ], 25 25 'resolve' => [ 26 - 'not_owner' => 'เฉพาะผู้เริ่มกระทู้ และเจ้าของบีตแม็ปสามารถทำเครื่องหมายว่าการสนทนาถูกแก้ไขแล้ว', 26 + 'not_owner' => 'เฉพาะผู้เริ่มกระทู้ และเจ้าของบีทแมพสามารถทำเครื่องหมายว่าการสนทนาถูกแก้ไขแล้ว', 27 27 ], 28 28 29 29 'store' => [ ··· 34 34 'bot' => "ไม่สามารถโหวตบนการสนทนาที่สร้างขึ้นโดยบอต", 35 35 'limit_exceeded' => 'กรุณารอสักครู่ก่อนโหวตเพิ่ม', 36 36 'owner' => "ไม่สามารถโหวตการสนทนาของตัวเองได้", 37 - 'wrong_beatmapset_state' => 'สามารถโหวตในการสนทนาของบีตแม็ปที่อยู่ในสถานะอยู่ระหว่างดำเนินการเท่านั้น', 37 + 'wrong_beatmapset_state' => 'สามารถโหวตในการสนทนาของบีทแมพที่อยู่ในสถานะอยู่ระหว่างดำเนินการเท่านั้น', 38 38 ], 39 39 ], 40 40 ··· 53 53 ], 54 54 55 55 'beatmapset' => [ 56 - 'discussion_locked' => 'บีตแม็ปนี้ถูกล็อคไว้สำหรับการสนทนา', 56 + 'discussion_locked' => 'บีทแมพนี้ถูกล็อคไว้สำหรับการสนทนา', 57 57 58 58 'metadata' => [ 59 - 'nominated' => 'คุณไม่สามารถเปลี่ยน metadata ของบีตแม็ปที่ทำการเสนอชื่อเป็นที่เรียบร้อยแล้ว ติดต่อ BN หรือ NAT หากคุณคิดว่ามีข้อผิดพลาดประการใด', 59 + 'nominated' => 'คุณไม่สามารถเปลี่ยน metadata ของบีทแมพที่ทำการเสนอชื่อเป็นที่เรียบร้อยแล้ว ติดต่อ BN หรือ NAT หากคุณคิดว่ามีข้อผิดพลาดประการใด', 60 60 ], 61 61 ], 62 62 ··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'เจ้าของคะแนนเท่านั้นที่ปักหมุดคะแนนได้', 175 176 'too_many' => 'ปักหมุดคะแนนเยอะเกินไป', 176 177 ],
+1 -1
resources/lang/th/beatmap_discussion_posts.php
··· 5 5 6 6 return [ 7 7 'index' => [ 8 - 'title' => 'โพสต์การสนทนาบีตแม็ป', 8 + 'title' => 'โพสต์การสนทนาบีทแมพ', 9 9 ], 10 10 11 11 'item' => [
+2 -2
resources/lang/th/beatmap_discussions.php
··· 19 19 'index' => [ 20 20 'deleted_beatmap' => 'ถูกลบไปแล้ว', 21 21 'none_found' => 'ไม่พบการสนทนาตามเกณฑ์การค้นหาที่เลือก', 22 - 'title' => 'การสนทนาเกี่ยวกับบีตแม็ป', 22 + 'title' => 'การสนทนาเกี่ยวกับบีทแมพ', 23 23 24 24 'form' => [ 25 25 '_' => 'ค้นหา', 26 26 'deleted' => 'รวมการสนทนาที่ถูกลบ', 27 - 'mode' => 'โหมดของบีตแม็ป', 27 + 'mode' => 'โหมดของบีทแมพ', 28 28 'only_unresolved' => 'มองเห็นเฉพาะการสนทนา/ปัญหาที่ยังไม่ได้แก้', 29 29 'types' => 'ชนิดของข้อความ', 30 30 'username' => 'ชื่อผู้ใช้',
+2 -2
resources/lang/th/beatmappacks.php
··· 8 8 'description' => 'แพ็คคอลเล็คชั่นของเพลงที่อยู่ในประเภทเดียวกัน', 9 9 'empty' => 'เร็วๆ นี้!', 10 10 'nav_title' => 'รายการ', 11 - 'title' => 'แพ็คบีตแม็ป', 11 + 'title' => 'แพ็คบีทแมพ', 12 12 13 13 'blurb' => [ 14 14 'important' => 'กรุณาอ่านก่อนทำการดาวน์โหลด', 15 15 'install_instruction' => 'การติดตั้ง: หลังจากที่แพ็คเกจดาวน์โหลดเสร็จแล้ว แยกเนื้อหาในแพ็กเกจไปที่โฟลเดอร์ Songs ของ osu! และ osu! จะจัดการที่เหลือ', 16 16 'note' => [ 17 - '_' => 'แล้วก็ทางเราแนะนำให้คุณ :scary, เนื่องจากคุณภาพของบีตแม็ปสมัยก่อนนั้นต่ำกว่าในสมัยนี้', 17 + '_' => 'แล้วก็ทางเราแนะนำให้คุณ :scary, เนื่องจากคุณภาพของบีทแมพสมัยก่อนนั้นต่ำกว่าในสมัยนี้', 18 18 'scary' => 'ดาวน์โหลดไฟล์จากล่าสุดไปเก่าสุด', 19 19 ], 20 20 ],
+17 -17
resources/lang/th/beatmaps.php
··· 55 55 ], 56 56 57 57 'message_hint' => [ 58 - 'in_general' => 'โพสต์นี้จะไปที่การสนทนาทั่วไป ถ้าอยากวิจารณ์บีตแม็ปนี้ เริ่มต้นข้อความของคุณด้วยช่วงเวลา (เช่น 00:12:345)', 58 + 'in_general' => 'โพสต์นี้จะไปที่การสนทนาทั่วไป ถ้าอยากวิจารณ์บีทแมพนี้ เริ่มต้นข้อความของคุณด้วยช่วงเวลา (เช่น 00:12:345)', 59 59 'in_timeline' => 'ในการวิจารณ์หลายช่วงเวลา โพสต์หลายๆครั้ง (หนึ่งโพสต์ต่อหนึ่งช่วงเวลา)', 60 60 ], 61 61 ··· 138 138 ], 139 139 140 140 'status-messages' => [ 141 - 'approved' => 'บีตแม็ปนี้ถูกอนุมัติในวันที่ :date', 142 - 'graveyard' => "บีตแม็ปนี้ไม่ถูกอัปเดตตั้งแต่ :date และน่าจะถูกละทิ้งโดยผู้ทำแมพไปแล้ว", 143 - 'loved' => 'บีตแม็ปนี้ถูกเพิ่มไปยัง "ชื่นชอบ" แล้วเมื่อวันที่ :date!', 144 - 'ranked' => 'บีตแม็ปนี้ถูกจัดอันดับแล้วในวันที่ :date', 145 - 'wip' => 'บีตแม็ปนี้ถูกทำเครื่องหมายไว้ว่าอยู่ในระหว่างการทำ', 141 + 'approved' => 'บีทแมพนี้ถูกอนุมัติในวันที่ :date', 142 + 'graveyard' => "บีทแมพนี้ไม่ถูกอัปเดตตั้งแต่ :date และน่าจะถูกละทิ้งโดยผู้ทำแมพไปแล้ว", 143 + 'loved' => 'บีทแมพนี้ถูก Loved ในวันที่ :date', 144 + 'ranked' => 'บีทแมพนี้ถูกจัดอันดับในวันที่ :date', 145 + 'wip' => 'บีทแมพนี้ถูกทำเครื่องหมายไว้ว่าอยู่ในระหว่างการทำ', 146 146 ], 147 147 148 148 'votes' => [ ··· 158 158 ], 159 159 160 160 'hype' => [ 161 - 'button' => 'Hype บีตแม็ป!', 161 + 'button' => 'Hype บีทแมพ!', 162 162 'button_done' => 'Hype ไปแล้ว!', 163 163 'confirm' => "แน่ใจหรอ นี่จะใช้หนึ่งใน :n Hype ที่เหลือของคุณและไม่สามารถแก้ไขได้", 164 - 'explanation' => 'Hype บีตแม็ปนี้เพื่อทำให้ง่ายขึ้นต่อการเสนอชื่อและจัดอันดับ', 165 - 'explanation_guest' => 'ลงชื่อเข้าใช้และ Hype บีตแม็ปนี้เพื่อทำให้ง่ายขึ้นต่อการเสนอชื่อและจัดอันดับ', 164 + 'explanation' => 'Hype บีทแมพนี้เพื่อทำให้ง่ายขึ้นต่อการเสนอชื่อและจัดอันดับ', 165 + 'explanation_guest' => 'ลงชื่อเข้าใช้และ Hype บีทแมพนี้เพื่อทำให้ง่ายขึ้นต่อการเสนอชื่อและจัดอันดับ', 166 166 'new_time' => "คุณจะได้ Hype ใหม่ใน :new_time", 167 167 'remaining' => 'คุณมี Hype เหลือ :remaining อัน', 168 168 'required_text' => 'Hype: :current/:required', ··· 175 175 ], 176 176 177 177 'nominations' => [ 178 - 'already_nominated' => 'คุณได้เสนอชื่อบีตแม็ปนี้แล้ว', 179 - 'cannot_nominate' => 'คุณไม่สามารถเสนอชื่อโหมดเกมของบีตแม็ปนี้ได้', 178 + 'already_nominated' => 'คุณได้เสนอชื่อบีทแมพนี้แล้ว', 179 + 'cannot_nominate' => 'คุณไม่สามารถเสนอชื่อโหมดเกมของบีทแมพนี้ได้', 180 180 'delete' => 'ลบ', 181 - 'delete_own_confirm' => 'คุณแน่ใจใช่ไหม? บีตแม็ปจะถูกลบและคุณจะถูกนำกลับไปยังหน้าโปรไฟล์ของคุณ', 181 + 'delete_own_confirm' => 'คุณแน่ใจใช่ไหม? บีทแมพจะถูกลบและคุณจะถูกนำกลับไปยังหน้าโปรไฟล์ของคุณ', 182 182 'delete_other_confirm' => 'คุณแน่ใจใช่ไหม? บีทแมพจะถูกลบและคุณจะถูกนำกลับไปยังหน้าโปรไฟล์ของผู้เล่น', 183 183 'disqualification_prompt' => 'เหตุผลในการตัดสิทธิ์?', 184 184 'disqualified_at' => 'ถูกตัดสิทธิ์เมื่อ :time_ago เพราะ (:reason)', ··· 187 187 'incorrect_state' => 'เกิดข้อผิดพลาดในการดำเนินการ ลองรีเฟรชหน้าเพจนี้ดู', 188 188 'love' => 'ชอบ', 189 189 'love_choose' => 'เลือกระดับความยากสำหรับ Loved', 190 - 'love_confirm' => 'ชอบบีตแม็ปนี้หรือไม่?', 190 + 'love_confirm' => 'ชอบบีทแมพนี้หรือ?', 191 191 'nominate' => 'เสนอชื่อ', 192 - 'nominate_confirm' => 'เสนอชื่อบีตแม็ปนี้?', 192 + 'nominate_confirm' => 'เสนอชื่อบีทแมพนี้?', 193 193 'nominated_by' => 'เสนอชื่อโดย :users', 194 194 'not_enough_hype' => "ไม่มี Hype เพียงพอ", 195 195 'remove_from_loved' => 'ถูกนำออกจาก Loved', ··· 214 214 'reset_confirm' => [ 215 215 'disqualify' => 'คุณแน่ใจใช่หรือไม่? ที่จะลบบีทแมพออกและรีเซ็ตความคืบหน้า', 216 216 'nomination_reset' => 'คุณแน่ใจหรือ? ในการโพสต์ปัญหาใหม่จะรีเซ็ตการเสนอชื่อ', 217 - 'problem_warning' => 'คุณแน่ใจที่จะรายงานปัญหาบน Beatmap นี้หรือไม่ รายงานนี้จะถูกแจ้งเตือนไปยัง Beatmap Nominators', 217 + 'problem_warning' => 'คุณแน่ใจที่จะรายงานปัญหาบนบีทแมพนี้หรือไม่ รายงานนี้จะถูกแจ้งเตือนไปยัง Beatmap Nominators', 218 218 ], 219 219 ], 220 220 ··· 256 256 ], 257 257 ], 258 258 'general' => [ 259 - 'converts' => 'รวมบีตแม็ปที่แปลงแล้ว', 259 + 'converts' => 'รวมบีทแมพที่แปลงแล้ว', 260 260 'featured_artists' => 'ศิลปินโดดเด่น', 261 261 'follows' => 'ติดตามผู้ทำแมพ', 262 262 'recommended' => 'ระดับความยากที่แนะนำ', 263 - 'spotlights' => 'บีตแม็ปที่โดดเด่น', 263 + 'spotlights' => 'บีทแมพที่โดดเด่น', 264 264 ], 265 265 'mode' => [ 266 266 'all' => 'ทั้งหมด',
+1 -1
resources/lang/th/beatmapset_discussion_votes.php
··· 5 5 6 6 return [ 7 7 'index' => [ 8 - 'title' => 'โหวตการสนทนาบีตแม็ป', 8 + 'title' => 'โหวตการสนทนาบีทแมพ', 9 9 ], 10 10 11 11 'item' => [
+4 -4
resources/lang/th/beatmapset_events.php
··· 6 6 return [ 7 7 'event' => [ 8 8 'approve' => 'อนุมัติ', 9 - 'beatmap_owner_change' => 'เจ้าของระดับความยาก:beatmapเปลี่ยนเป็น:new_user', 9 + 'beatmap_owner_change' => 'เจ้าของระดับความยาก :beatmap เปลี่ยนเป็น :new_user', 10 10 'discussion_delete' => 'ผู้ดูแลลบการสนทนา :discussion', 11 - 'discussion_lock' => 'การสนทนาสำหรับบีตแม็ปนี้ถูกปิดใช้งาน (:text)', 11 + 'discussion_lock' => 'การสนทนาสำหรับบีทแมพนี้ถูกปิดใช้งาน (:text)', 12 12 'discussion_post_delete' => 'ผู้ดูแลลบโพสต์จากการสนทนา:discussion', 13 13 'discussion_post_restore' => 'ผู้ดูแลกู้คืนโพสต์จากการสนทนา :discussion', 14 14 'discussion_restore' => 'ผู้ดูแลกู้คืนการสนทนา :discussion', 15 - 'discussion_unlock' => 'การสนทนาสำหรับบีตแม็ปนี้ถูกเปิดใช้งาน', 15 + 'discussion_unlock' => 'การสนทนาสำหรับบีทแมพนี้ถูกเปิดใช้งาน', 16 16 'disqualify' => 'ถูกตัดสิทธิ์โดย :user ด้วยเหตุผล :discussion (:text)', 17 17 'disqualify_legacy' => 'ถูกตัดสิทธิ์โดย :user: ด้วยเหตุผล :text', 18 18 'genre_edit' => 'แก้ไขหมวดจาก :old เป็น :new', ··· 43 43 ], 44 44 45 45 'index' => [ 46 - 'title' => 'กิจกรรมของเซ็ทบีตแม็ป', 46 + 'title' => 'กิจกรรมของเซ็ทบีทแมพ', 47 47 48 48 'form' => [ 49 49 'period' => 'ระยะเวลา',
+4 -4
resources/lang/th/beatmapset_watches.php
··· 5 5 6 6 return [ 7 7 'index' => [ 8 - 'description' => 'นี่คือรายการสนทนาบีตแม็ปที่คุณกำลังติดตามอยู่ คุณจะได้รับการแจ้งเตือนเมื่อมีโพสต์หรืออัปเดตใหม่', 8 + 'description' => 'นี่คือรายการสนทนาบีทแมพที่คุณกำลังติดตามอยู่ คุณจะได้รับการแจ้งเตือนเมื่อมีโพสต์หรืออัปเดตใหม่', 9 9 'title_compact' => 'รายการวิจารณ์ที่ติดตาม', 10 10 11 11 'counts' => [ 12 - 'total' => 'บีตแม็ปที่ดูอยู่', 13 - 'unread' => 'บีตแม็ปที่มีการเคลื่อนไหว', 12 + 'total' => 'บีทแมพที่ดูอยู่', 13 + 'unread' => 'บีทแมพที่มีการเคลื่อนไหว', 14 14 ], 15 15 16 16 'table' => [ 17 - 'empty' => 'ยังไม่มีการสนทนาบีตแม็ปที่ติดตามอยู่', 17 + 'empty' => 'ยังไม่มีการสนทนาบีทแมพที่ติดตามอยู่', 18 18 'last_update' => 'อัปเดตล่าสุด', 19 19 'open_issues' => 'ปัญหา', 20 20 'state' => 'สถานะ',
+20 -20
resources/lang/th/beatmapsets.php
··· 5 5 6 6 return [ 7 7 'availability' => [ 8 - 'disabled' => 'บีตแม็ปนี้ยังไม่สามารถดาวน์โหลดได้', 9 - 'parts-removed' => 'บางส่วนของบีตแม็ปนี้ถูกลบตามคำขอของผู้แต่งหรือผู้ถือสิทธิ์บุคคลสาม', 8 + 'disabled' => 'บีทแมพนี้ยังไม่สามารถดาวน์โหลดได้', 9 + 'parts-removed' => 'บางส่วนของบีทแมพนี้ถูกลบตามคำขอของผู้แต่งหรือผู้ถือสิทธิ์บุคคลสาม', 10 10 'more-info' => 'เช็คที่นี่เพื่อดูรายละเอียดเพิ่มเติม', 11 11 'rule_violation' => 'เนื้อหาบางส่วนในแมพนี้ได้ถูกนำออกเนื่องจากถูกตัดสินว่าไม่เหมาะสมใน osu!', 12 12 ], 13 13 14 14 'cover' => [ 15 - 'deleted' => 'บีตแม็ปที่ถูกลบ', 15 + 'deleted' => 'บีทแมพที่ถูกลบ', 16 16 ], 17 17 18 18 'download' => [ ··· 24 24 ], 25 25 26 26 'index' => [ 27 - 'title' => 'รายการบีตแม็ป', 28 - 'guest_title' => 'บีตแม็ป', 27 + 'title' => 'รายการบีทแมพ', 28 + 'guest_title' => 'บีทแมพ', 29 29 ], 30 30 31 31 'panel' => [ 32 - 'empty' => 'ไม่มีบีตแม็ป', 32 + 'empty' => 'ไม่มีบีทแมพ', 33 33 34 34 'download' => [ 35 35 'all' => 'ดาวน์โหลด', ··· 47 47 48 48 'dialog' => [ 49 49 'confirmation' => 'คุณแน่ใจที่จะเสนอชื่อแมพนี้ใช่ไหม', 50 - 'header' => 'เสนอชื่อบีตแม็ป', 50 + 'header' => 'เสนอชื่อบีทแมพ', 51 51 'hybrid_warning' => 'โน้ต: คุณสามารถเสนอชื่อได้เพียงแค่ครั้งเดียว ดังนั้นโปรดตรวจสอบให้แน่ใจว่าคุณเสนอชื่อในเกมโหมดทั้งหมดที่คุณต้องการจะเสนอชื่อ', 52 52 'which_modes' => 'เสนอชื่อให้โหมดไหน', 53 53 ], ··· 61 61 'discussion' => 'การสนทนา', 62 62 63 63 'deleted_banner' => [ 64 - 'title' => 'บีตแม็ปนี้ถูกลบไปแล้ว', 64 + 'title' => 'บีทแมพนี้ถูกลบไปแล้ว', 65 65 'message' => '(ผู้ดูแลเท่านั้นที่สามารถเห็นสิ่งนี้)', 66 66 ], 67 67 68 68 'details' => [ 69 69 'by_artist' => 'โดย :artist', 70 - 'favourite' => 'ชื่นชอบบีตแม็ปนี้', 71 - 'favourite_login' => 'ลงชื่อเข้าใช้เพื่อเพิ่มบีตแม็ปนี้เข้าในรายการโปรด', 72 - 'logged-out' => 'คุณต้องเข้าสู่ระบบก่อนที่จะดาวน์โหลดบีตแม็ป', 70 + 'favourite' => 'ชื่นชอบบีทแมพนี้', 71 + 'favourite_login' => 'ลงชื่อเข้าใช้เพื่อเพิ่มบีทแมพนี้เข้าในรายการโปรด', 72 + 'logged-out' => 'คุณต้องเข้าสู่ระบบก่อนที่จะดาวน์โหลดบีทแมพ', 73 73 'mapped_by' => 'แมพโดย :mapper', 74 74 'mapped_by_guest' => 'ระดับความยากโดย :mapper', 75 - 'unfavourite' => 'นำบีตแม็ปนี้ออกจากรายการโปรด', 75 + 'unfavourite' => 'นำบีทแมพนี้ออกจากรายการโปรด', 76 76 'updated_timeago' => 'อัปเดตล่าสุดเมื่อ :timeago', 77 77 78 78 'download' => [ ··· 98 98 ], 99 99 100 100 'favourites' => [ 101 - 'limit_reached' => 'คุณมีบีตแม็ปในรายการโปรดมากเกินไป! กรุณาเอาออกบ้างแล้วลองอีกครั้ง', 101 + 'limit_reached' => 'คุณมีบีทแมพที่ชื่นชอบมากเกินไป! กรุณาเอาออกบ้างแล้วลองอีกครั้ง', 102 102 ], 103 103 104 104 'hype' => [ ··· 115 115 ], 116 116 117 117 'disqualify' => [ 118 - '_' => 'ถ้าคุณพบปัญหากับบีตแม็ปนี้ ให้คุณยกเลิกสถานะ "ผ่านการรับรอง" ของบีตแม็ปนี้ออก :link', 118 + '_' => 'ถ้าคุณพบปัญหากับบีทแมพนี้ ให้คุณยกเลิกสถานะ "ผ่านการรับรอง" ของบีทแมพนี้ออก :link', 119 119 ], 120 120 121 121 'report' => [ 122 - '_' => 'หากคุณพบปัญหาเกี่ยวกับบีตแม็ปนี้ โปรดรายงานที่ :link เพื่อแจ้งให้ทีมงานทราบ', 122 + '_' => 'ถ้าคุณพบปัญหากับบีทแมพนี้ โปรดรายงานให้เราทราบผ่าน :link', 123 123 'button' => 'รายงานปัญหา', 124 124 'link' => 'ที่นี่', 125 125 ], ··· 135 135 'offset' => 'ออฟเซ็ตออนไลน์', 136 136 'points-of-failure' => 'ความล้มเหลว', 137 137 'source' => 'แหล่งที่มา', 138 - 'storyboard' => 'บีตแม็ปนี้มีเนื้อเรื่อง', 138 + 'storyboard' => 'บีทแมพนี้มี storyboard', 139 139 'success-rate' => 'อัตราการผ่าน', 140 140 'tags' => 'แท็ก', 141 - 'video' => 'บีตแม็ปนี้มีวิดีโอ', 141 + 'video' => 'บีทแมพนี้มีวิดีโอ', 142 142 ], 143 143 144 144 'nsfw_warning' => [ 145 - 'details' => 'บีตแม็ปนี้มีเนื้อหาไม่เหมาะสม, รุนแรง, หรือรบกวนใจ คุณยังจะต้องการดูมันไหม', 145 + 'details' => 'บีทแมพนี้มีเนื้อหาไม่เหมาะสม, รุนแรง, หรือรบกวนใจ คุณยังจะต้องการดูมันไหม', 146 146 'title' => 'เนื้อหาไม่เหมาะสม', 147 147 148 148 'buttons' => [ 149 149 'disable' => 'ปิดการแจ้งเตือน', 150 - 'listing' => 'รายชื่อบีตแม็ป', 150 + 'listing' => 'รายชื่อบีทแมพ', 151 151 'show' => 'แสดง', 152 152 ], 153 153 ], ··· 181 181 'friend' => 'ยังไม่มีใครในเพือนของคุณที่ทำคะแนนบนแมพนี้ได้!', 182 182 'global' => 'ยังไม่มีคะแนน บางทีคุณอาจจะลองทำดูนะ', 183 183 'loading' => 'กำลังโหลดคะแนน...', 184 - 'unranked' => 'บีตแม็ปที่ไม่ได้จัดอันดับ', 184 + 'unranked' => 'บีทแมพที่ไม่ได้จัดอันดับ', 185 185 ], 186 186 'score' => [ 187 187 'first' => 'สูงสุด',
+1 -1
resources/lang/th/comments.php
··· 17 17 'title' => 'ความคิดเห็น', 18 18 19 19 'commentable_name' => [ 20 - 'beatmapset' => 'บีตแม็ป', 20 + 'beatmapset' => 'บีทแมพ', 21 21 'build' => 'การเปลี่ยนแปลง', 22 22 'news_post' => 'ข่าวสาร', 23 23 '_deleted' => 'รายการที่ถูกลบ',
+11 -11
resources/lang/th/community.php
··· 46 46 'title' => 'โอ? ฉันได้อะไรบ้างเหรอ?!', 47 47 'osu_direct' => [ 48 48 'title' => 'osu!direct', 49 - 'description' => 'ระบบหาบีตแม็ปที่ง่ายและเร็วโดยไม่ต้องออกจากเกม', 49 + 'description' => 'ระบบหาบีทแมพที่ง่ายและเร็วโดยไม่ต้องออกจากเกม', 50 50 ], 51 51 52 52 'friend_ranking' => [ 53 53 'title' => 'อันดับคะแนนของเพื่อน', 54 - 'description' => "ดูว่าคะแนนบีตแม็ปของตัวเองกับเพื่อนใครเจ๋งกว่ากัน ทั้งในเกมและบนเว็บ", 54 + 'description' => "ดูว่าคะแนนบีทแมพของตัวเองกับเพื่อนใครเจ๋งกว่ากัน ทั้งในเกมและบนเว็บ", 55 55 ], 56 56 57 57 'country_ranking' => [ ··· 66 66 67 67 'auto_downloads' => [ 68 68 'title' => 'การดาวน์โหลดอัตโนมัติ', 69 - 'description' => 'โหลดบีตแม็ปอัตโนมัติตอนเล่นหลายคน ดูคนอื่นเล่น หรือแค่กดลิงก์ในช่องแชท', 69 + 'description' => 'โหลดบีทแมพอัตโนมัติตอนเล่นหลายคน ดูคนอื่นเล่น หรือแค่กดลิงก์ในช่องแชต', 70 70 ], 71 71 72 72 'upload_more' => [ 73 - 'title' => 'อัปโหลดบีตแม็ปเพิ่ม', 74 - 'description' => 'ช่องอัปโหลดบีตแม็ปเพิ่มเติม (ต่อแม็ปจัดอันดับที่มีอยู่) มากถึง 10 แมพ', 73 + 'title' => 'อัปโหลดบีทแมพเพิ่ม', 74 + 'description' => 'ช่องอัปโหลดบีทแมพเพิ่มเติม (ต่อแมพจัดอันดับที่มีอยู่) มากถึง 10 แมพ', 75 75 ], 76 76 77 77 'early_access' => [ ··· 85 85 ], 86 86 87 87 'beatmap_filters' => [ 88 - 'title' => 'ตัวกรองบีตแม็ป', 89 - 'description' => 'กรองบีตแม็ปที่เล่นแล้ว/ยังไม่เล่น และแรงก์ที่เคยได้', 88 + 'title' => 'ตัวกรองบีทแมพ', 89 + 'description' => 'กรองบีทแมพที่เล่นแล้ว/ยังไม่เล่น และแรงก์ที่เคยได้', 90 90 ], 91 91 92 92 'yellow_fellow' => [ ··· 120 120 ], 121 121 122 122 'more_favourites' => [ 123 - 'title' => 'เพิ่มจำนวนบีตแม็ปที่คุณสามารถเลือกเป็นรายการโปรด', 124 - 'description' => 'จำนวนบีตแม็ปที่คุณชื่นชอบได้เพิ่มจาก :normally &rarr; :supporter', 123 + 'title' => 'เพิ่มจำนวนบีทแมพที่คุณสามารถเลือกเป็นรายการโปรด', 124 + 'description' => 'จำนวนบีทแมพที่คุณชื่นชอบได้เพิ่มจาก :normally &rarr; :supporter', 125 125 ], 126 126 'more_friends' => [ 127 127 'title' => 'เพิ่มจำนวนเพื่อนที่คุณสามารถมีได้', 128 128 'description' => 'จำนวนเพื่อนที่คุณมีได้สูงสุดเพิ่มจาก :normally &rarr; :supporter', 129 129 ], 130 130 'more_beatmaps' => [ 131 - 'title' => 'อัปโหลดบีตแม็ปเพิ่ม', 132 - 'description' => 'จำนวนบีตแม็ปที่รอดำเนินการที่คุณสามารถมีได้ในคราวเดียวจะคำนวณจากค่าฐานบวกโบนัสเพิ่มเติมสำหรับบีตแม็ปจัดอันดับแต่ละอันที่คุณมีอยู่ในปัจจุบัน (ไม่เกินขีดจำกัด)<br/><br/>โดยปกติจะเป็น :base บวก :bonus ต่อ บีตแม็ปจัดอันดับ (สูงสุด :bonus_max) สำหรับผู้สนับสนุน สิ่งนี้จะเพิ่มเป็น :supporter_base บวก :supporter_bonus ต่อบีตแม็ปจัดอันดับ (สูงสุด :supporter_bonus_max)', 131 + 'title' => 'อัปโหลดบีทแมพเพิ่ม', 132 + 'description' => 'จำนวนบีทแมพที่ไม่ได้จัดอันดับ ณ เวลาใด ๆ จะขึ้นกับค่าเริ่มต้น + โบนัสต่อจำนวนบีทแมพที่ได้จัดอันดับ (สูงสุดตามขีดจำกัดที่มี)<br/><br/>ปกติแล้วคือ :base + :bonus บีทแมพต่อบีทแมพที่ได้จัดอันดับ (สูงสุด :bonus_max) หากเป็นผู้สนับสนุน จะกลายเป็น :supporter_base + :supporter_bonus บีทแมพ (สูงสุด :supporter_bonus_max)', 133 133 ], 134 134 'friend_filtering' => [ 135 135 'title' => 'อันดับคะแนนเพื่อน',
+2 -2
resources/lang/th/contest.php
··· 19 19 'show_voted_only' => 'แสดงโหวต', 20 20 21 21 'best_of' => [ 22 - 'none_played' => "ดูเหมือนคุณจะไม่ได้เล่น beatmap ที่เข้าประกวดอยู่นะ", 22 + 'none_played' => "ดูเหมือนคุณจะไม่ได้เล่นบีทแมพที่เข้าประกวดอยู่นะ", 23 23 ], 24 24 25 25 'button' => [ ··· 34 34 35 35 'requirement' => [ 36 36 'playlist_beatmapsets' => [ 37 - 'incomplete_play' => 'ต้องเล่นบีตแม็ปทั้งหมดในเพลย์ลิสต์ที่กำหนดก่อนลงคะแนน', 37 + 'incomplete_play' => 'ต้องเล่นบีทแมพทั้งหมดในเพลย์ลิสต์ที่กำหนดก่อนลงคะแนน', 38 38 ], 39 39 ], 40 40 ],
+2 -2
resources/lang/th/events.php
··· 9 9 'beatmapset_approve' => ':beatmapset โดย <strong>:user</strong> ได้ถูกอนุมัติแล้ว!', 10 10 'beatmapset_delete' => ':beatmapset ถูกลบแล้ว', 11 11 'beatmapset_revive' => ':beatmapset ได้ถูกชุบชีวิตขึ้นมาอีกครั้งโดย <strong>:user</strong>.', 12 - 'beatmapset_update' => '<strong><em>:user</em></strong> ได้อัพเดต beatmap ที่มีชื่อว่า "<em>:beatmapset</em>"', 13 - 'beatmapset_upload' => '<strong><em>:user</em></strong> ได้ทำการเพิ่ม beatmap ใหม่ ":beatmapset"', 12 + 'beatmapset_update' => '<strong><em>:user</em></strong> ได้อัพเดตบีทแมพที่มีชื่อว่า "<em>:beatmapset</em>"', 13 + 'beatmapset_upload' => '<strong><em>:user</em></strong> ได้ทำการเพิ่มบีทแมพใหม่ ":beatmapset"', 14 14 'empty' => "ผู้ใช้รายนี้ยังไม่ได้ทำอะไรน่าสนใจในช่วงนี้", 15 15 'rank' => '<strong><em>:user</em></strong> ได้อันดับที่ #:rank ในเพลง <em>:beatmap</em> (:mode)', 16 16 'rank_lost' => '<strong><em>:user</em></strong> เสียอันดับที่ 1 ในเพลง <em>:beatmap</em> (:mode)',
+6 -6
resources/lang/th/follows.php
··· 24 24 ], 25 25 26 26 'mapping' => [ 27 - 'empty' => 'ไม่มีผู้สร้างบีตแม็ปที่ติดตามอยู่', 27 + 'empty' => 'ไม่มีผู้สร้างบีทแมพที่ติดตามอยู่', 28 28 'followers' => 'ผู้ติดตามการแมพ', 29 - 'page_title' => 'รายการการติดตามผู้สร้างบีตแม็ป', 30 - 'title' => 'ผู้สร้างบีตแม็ป', 31 - 'to_0' => 'หยุดเตือนเมื่อผู้เล่นคนนี้อัปโหลดบีตแม็ปใหม่', 32 - 'to_1' => 'เตือนฉันเมื่อผู้เล่นคนนี้อัปโหลดบีตแม็ปใหม่', 29 + 'page_title' => 'รายการการติดตามผู้สร้างบีทแมพ', 30 + 'title' => 'ผู้สร้างบีทแมพ', 31 + 'to_0' => 'หยุดเตือนเมื่อผู้เล่นคนนี้อัปโหลดบีทแมพใหม่', 32 + 'to_1' => 'เตือนฉันเมื่อผู้เล่นคนนี้อัปโหลดบีทแมพใหม่', 33 33 ], 34 34 35 35 'modding' => [ 36 - 'title' => 'การสนทนาบีตแม็ป', 36 + 'title' => 'การสนทนาบีทแมพ', 37 37 ], 38 38 ];
+9 -9
resources/lang/th/home.php
··· 27 27 'title' => 'ค้นหา', 28 28 29 29 'beatmapset' => [ 30 - 'login_required' => 'เข้าสู่ระบบเพื่อค้นหาบีตแม็ป', 31 - 'more' => ':count ผลการค้นหาบีตแม็ปเพิ่มเติม', 32 - 'more_simple' => 'ดูผลการค้นหาบีตแม็ปเพิ่มเติม', 33 - 'title' => 'บีตแม็ป', 30 + 'login_required' => 'เข้าสู่ระบบเพื่อค้นหาบีทแมพ', 31 + 'more' => ':count ผลการค้นหาบีทแมพเพิ่มเติม', 32 + 'more_simple' => 'ดูผลการค้นหาบีทแมพเพิ่มเติม', 33 + 'title' => 'บีทแมพ', 34 34 ], 35 35 36 36 'forum_post' => [ ··· 51 51 52 52 'mode' => [ 53 53 'all' => 'ทั้งหมด', 54 - 'beatmapset' => 'บีตแม็ป', 54 + 'beatmapset' => 'บีทแมพ', 55 55 'forum_post' => 'ฟอรั่ม', 56 56 'user' => 'ผู้เล่น', 57 57 'wiki_page' => 'วิกิ', ··· 111 111 'description' => 'กดปุ่มข้างบนเพื่อดาวน์โหลดตัวติดตั้งและรัน', 112 112 ], 113 113 'beatmaps' => [ 114 - 'title' => 'โหลดบีตแม็ป', 114 + 'title' => 'โหลดบีทแมพ', 115 115 'description' => [ 116 - '_' => ':browse ห้องสมุดขนาดใหญ่ของบีตแม็ปที่ผู้สร้างสร้างขึ้นและเริ่มเล่นได้เลย!', 116 + '_' => ':browse บีทแมพมากมายที่ผู้เล่นต่าง ๆ ได้สร้างขึ้น และเริ่มเล่น!', 117 117 'browse' => 'ค้นหา', 118 118 ], 119 119 ], ··· 134 134 ], 135 135 ], 136 136 'beatmaps' => [ 137 - 'new' => 'บีตแม็ปจัดอันดับใหม่ล่าสุด', 138 - 'popular' => 'บีตแม็ปยอดฮิต', 137 + 'new' => 'บีทแมพจัดอันดับใหม่ล่าสุด', 138 + 'popular' => 'บีทแมพยอดฮิต', 139 139 'by_user' => 'โดย :user', 140 140 ], 141 141 'buttons' => [
+4 -4
resources/lang/th/layout.php
··· 14 14 15 15 'header' => [ 16 16 'admin' => [ 17 - 'beatmapset' => 'บีตแม็ปเซ็ท', 18 - 'beatmapset_covers' => 'ปกบีตแม็ปเซ็ท', 17 + 'beatmapset' => 'บีทแมพเซ็ท', 18 + 'beatmapset_covers' => 'ปกหลังบีทแมพเซ็ท', 19 19 'contest' => 'การแข่งขัน', 20 20 'contests' => 'การแข่งขัน', 21 21 'root' => 'แผงควบคุม', ··· 67 67 68 68 'menu' => [ 69 69 'beatmaps' => [ 70 - '_' => 'บีตแม็ป', 70 + '_' => 'บีทแมพ', 71 71 ], 72 72 'community' => [ 73 73 '_' => 'ชุมชน', ··· 98 98 '_' => 'ทั่วไป', 99 99 'home' => 'หน้าแรก', 100 100 'changelog-index' => 'บันทึกการเปลี่ยนแปลง', 101 - 'beatmaps' => 'รายการบีตแม็ป', 101 + 'beatmaps' => 'รายการบีทแมพ', 102 102 'download' => 'ดาวน์โหลด osu!', 103 103 ], 104 104 'help' => [
+3 -3
resources/lang/th/mail.php
··· 5 5 6 6 return [ 7 7 'beatmapset_update_notice' => [ 8 - 'new' => 'ขอแจ้งให้คุณทราบว่ามีการอัปเดตใหม่ในบีตแม็ป ":title" ตั้งแต่การเข้าชมครั้งล่าสุดของคุณ', 9 - 'subject' => 'มีอัพเดตใหม่สำหรับบีตแม็ป ":title"', 10 - 'unwatch' => 'หากคุณไม่ต้องการดูบีตแม็ปนี้อีกต่อไป คุณสามารถคลิกลิงก์ "เลิกดู" ที่อยู่ในหน้าด้านบน หรือจากหน้ารายการเฝ้าดูของม็อตหรือการดัดแปลง:', 8 + 'new' => 'อยากจะบอกว่าตั้งแต่ออกจากกระทู้บีทแมพ ":title" ครั้งล่าสุด บีทแมพอัปเดตแล้ว', 9 + 'subject' => 'มีอัพเดตใหม่สำหรับบีทแมพ ":title"', 10 + 'unwatch' => 'ถ้าคุณไม่ต้องการที่จะติดตามบีทแมพนี้ต่อ คุณสามารถเลือกระหว่างการกดปุ่ม Unwatch ที่อยู่ในหน้าด้านบน และ การกดปุ่ม Unwatch ที่อยู่ในหน้า รายการ Mod ที่ติดตาม', 11 11 'visit' => 'เยี่ยมชมหน้าการสนทนาได้จากที่นี่', 12 12 ], 13 13
+1 -1
resources/lang/th/matches.php
··· 5 5 6 6 return [ 7 7 'match' => [ 8 - 'beatmap-deleted' => 'beatmap ที่ถูกลบ', 8 + 'beatmap-deleted' => 'บีทแมพที่ถูกลบ', 9 9 'failed' => 'ล้มเหลว', 10 10 'header' => 'แข่งขันแบบหลายคน', 11 11 'in-progress' => '(การแข่งขันกำลังดำเนินการ)',
+10 -10
resources/lang/th/model_validation.php
··· 13 13 14 14 'beatmapset_discussion' => [ 15 15 'beatmap_missing' => 'ช่วงเวลาได้ถูกกำหนดไว้แต่ไม่พบ Beatmap', 16 - 'beatmapset_no_hype' => "บีตแม็ปนี้ไม่สามารถ Hype ได้", 16 + 'beatmapset_no_hype' => "บีทแมพนี้ไม่สามารถ hype ได้", 17 17 'hype_requires_null_beatmap' => 'การ Hype ต้องทำในส่วนของทั่วไปเท่านั้น (ความยากทั้งหมด)', 18 18 'invalid_beatmap_id' => 'ระดับความยากไม่ได้เลือกอย่างถูกต้อง', 19 - 'invalid_beatmapset_id' => 'บีตแม็ปไม่ได้เลือกอย่างถูกต้อง', 19 + 'invalid_beatmapset_id' => 'บีทแมพไม่ได้เลือกอย่างถูกต้อง', 20 20 'locked' => 'การสนทนาได้ถูกล็อกไว้', 21 21 22 22 'attributes' => [ ··· 25 25 ], 26 26 27 27 'hype' => [ 28 - 'discussion_locked' => "ขณะนี้บีตแม็ปนี้ถูกล็อกไว้สำหรับการสนทนาและไม่สามารถ Hype ได้", 28 + 'discussion_locked' => "บีทแมพนี้ถูกจำกัดสิทธิในการสนทนา และ สิทธิในการ Hype", 29 29 'guest' => 'ต้องเข้าสู่ระบบก่อนถึงจะ Hype ได้', 30 - 'hyped' => 'คุณได้ Hype บีตแม็ปนี้แล้ว', 30 + 'hyped' => 'คุณได้ Hype บีทแมพนี้แล้ว', 31 31 'limit_exceeded' => 'คุณใช้ Hpye ทั้งหมดของคุณแล้ว', 32 - 'not_hypeable' => 'บีตแม็ปนี้ไม่สามารถ Hype ได้', 33 - 'owner' => 'ห้าม Hype ในบีตแม็ปของคุณเอง', 32 + 'not_hypeable' => 'บีทแมพนี้ไม่สามารถ Hype ได้', 33 + 'owner' => 'ห้าม Hype ในบีทแมปของคุณเอง', 34 34 ], 35 35 36 36 'timestamp' => [ 37 - 'exceeds_beatmapset_length' => 'เวลาประทับที่ระบุเกินความยาวของบีตแม็ป', 37 + 'exceeds_beatmapset_length' => 'เวลาประทับที่ระบุเกินความยาวของบีทแมพ', 38 38 'negative' => "เวลาประทับต้องไม่เป็นค่าลบ", 39 39 ], 40 40 ], ··· 72 72 ], 73 73 74 74 'post' => [ 75 - 'beatmapset_post_no_delete' => 'ไม่อนุญาตให้ลบโพสต์ Metadata ของบีตแม็ป', 76 - 'beatmapset_post_no_edit' => 'ไม่อนุญาตให้ดัดแปลงโพสต์ Metadata ของบีตแม็ป', 75 + 'beatmapset_post_no_delete' => 'ไม่อนุญาตให้ลบโพสต์ Metadata ของบีทแมพ', 76 + 'beatmapset_post_no_edit' => 'ไม่อนุญาตให้ดัดแปลงโพสต์ Metadata ของบีทแมพ', 77 77 'first_post_no_delete' => 'ไม่สามารถลบโพสต์ที่เริ่มต้นได้', 78 78 'missing_topic' => 'โพสต์ไม่มีหัวข้อ', 79 79 'only_quote' => 'การตอบกลับของคุณมีแค่คำพูด', ··· 174 174 ], 175 175 176 176 'user_report' => [ 177 - 'no_ranked_beatmapset' => 'ไม่สามารถรายงานบีตแม็ปที่จัดอันดับแล้วได้', 177 + 'no_ranked_beatmapset' => 'ไม่สามารถรายงานบีทแมพที่จัดอันดับแล้วได้', 178 178 'not_in_channel' => 'คุณไม่ได้อยู่ในช่องนี้', 179 179 'reason_not_valid' => ':reason ไม่สามารถใช้ได้กับการรายงานประเภทนี้', 180 180 'self' => "เดี๋ยว คุณรายงานตัวเองไม่ได้",
+25 -34
resources/lang/th/notifications.php
··· 15 15 16 16 'action_type' => [ 17 17 '_' => 'ทั้งหมด', 18 - 'beatmapset' => 'บีตแม็ป', 18 + 'beatmapset' => 'บีทแมพ', 19 19 'build' => 'เวอร์ชั่น', 20 20 'channel' => 'แชท', 21 21 'forum_topic' => 'ฟอรั่ม', ··· 26 26 'filters' => [ 27 27 '_' => 'ทั้งหมด', 28 28 'user' => 'โปรไฟล์', 29 - 'beatmapset' => 'บีตแม็ป', 29 + 'beatmapset' => 'บีทแมพ', 30 30 'forum_topic' => 'บอร์ดข่าวสาร', 31 31 'news_post' => 'ข่าวสาร', 32 32 'build' => 'เวอร์ชั่น', ··· 35 35 36 36 'item' => [ 37 37 'beatmapset' => [ 38 - '_' => 'บีตแม็ป', 38 + '_' => 'บีทแมพ', 39 39 40 40 'beatmap_owner_change' => [ 41 41 '_' => 'ระดับความยากของแขก', 42 - 'beatmap_owner_change' => 'ตอนนี้คุณเป็นเจ้าของระดับความยาก ":beatmap" สําหรับบีตแม็ป ":title"', 42 + 'beatmap_owner_change' => 'ตอนนี้คุณเป็นเจ้าของระดับความยาก ":beatmap" สําหรับบีทแมพ ":title"', 43 43 'beatmap_owner_change_compact' => 'ตอนนี้คุณเป็นเจ้าของระดับความยาก ":beatmap"', 44 44 ], 45 45 46 46 'beatmapset_discussion' => [ 47 - '_' => 'การสนทนาบีตแม็ป', 48 - 'beatmapset_discussion_lock' => 'บีตแม็ป ":title" ได้ถูกปิดการใช้งานการสนทนา', 47 + '_' => 'การสนทนาบีทแมพ', 48 + 'beatmapset_discussion_lock' => 'บีทแมพ ":title" ได้ถูกปิดการใช้งานการสนทนา', 49 49 'beatmapset_discussion_lock_compact' => 'การสนทนาได้ถูกล็อกไว้', 50 50 'beatmapset_discussion_post_new' => ':username ได้เขียนข้อความใหม่ใน ":title" การสนทนาของ beatmap', 51 51 'beatmapset_discussion_post_new_empty' => 'โพสใหม่ บน :title โดย :username', ··· 53 53 'beatmapset_discussion_post_new_compact_empty' => 'โพสใหม่โดย :username', 54 54 'beatmapset_discussion_review_new' => 'บทวิจารณ์ใหม่บน ":title" โดย :username มีปัญหาอยู่ :problems ปัญหา, คำแนะนำอยู่ :suggestions คำแนะนำ, คำชม :praises คำชม ', 55 55 'beatmapset_discussion_review_new_compact' => 'บทวิจารณ์โดย :username มีปัญหาอยู่ :problems ปัญหา, คำแนะนำอยู่ :suggestions คำแนะนำ, คำชม :praises คำชม ', 56 - 'beatmapset_discussion_unlock' => 'บีตแม็ป ":title" ได้ถูกเปิดการใช้งานในการสนทนาแล้ว', 56 + 'beatmapset_discussion_unlock' => 'บีทแมพ ":title" ได้ถูกเปิดการใช้งานในการสนทนาแล้ว', 57 57 'beatmapset_discussion_unlock_compact' => 'การสนทนาได้ถูกปลดล๊อค', 58 58 ], 59 59 60 60 'beatmapset_problem' => [ 61 - '_' => 'ปัญหาของบีตแม็ปที่ผ่านการรับรอง', 61 + '_' => 'ปัญหาของบีทแมพที่ผ่านการรับรอง', 62 62 'beatmapset_discussion_qualified_problem' => 'รายงานโดย :username บน :title :content', 63 63 'beatmapset_discussion_qualified_problem_empty' => 'รายงานโดย :username บน :title ', 64 64 'beatmapset_discussion_qualified_problem_compact' => 'รายงานโดย :username บน :content ', ··· 66 66 ], 67 67 68 68 'beatmapset_state' => [ 69 - '_' => 'สถานะของบีตแม็ปถูกเปลี่ยน', 69 + '_' => 'สถานะของบีทแมพถูกเปลี่ยน', 70 70 'beatmapset_disqualify' => '":title" ถูกตัดสิทธิ์', 71 - 'beatmapset_disqualify_compact' => 'บีตแม็ปถูกตัดสิทธิ์', 71 + 'beatmapset_disqualify_compact' => 'บีทแมพถูกตัดสิทธิ์', 72 72 'beatmapset_love' => '":title" ได้รับการเลื่อนระดับเป็นชื่นชอบ', 73 - 'beatmapset_love_compact' => 'บีตแม็ปได้รับการเลื่อนตำแหน่งเป็นรักเลย', 73 + 'beatmapset_love_compact' => 'บีทแมพได้รับการเลื่อนตำแหน่งเป็น Loved', 74 74 'beatmapset_nominate' => '":title" ได้รับการเสนอชื่อ', 75 - 'beatmapset_nominate_compact' => 'บีตแม็ปได้รับการเสนอชื่อเข้าชิง', 75 + 'beatmapset_nominate_compact' => 'บีทแมพได้รับการเสนอชื่อ', 76 76 'beatmapset_qualify' => '":title" ได้รับการเสนอชื่อเพียงพอที่จะเข้าคิวจัดอันดับ', 77 - 'beatmapset_qualify_compact' => 'บีตแม็ปเข้าสู่คิวการจัดอันดับ', 77 + 'beatmapset_qualify_compact' => 'บีทแมพได้เข้าการคิวจัดอันดับ', 78 78 'beatmapset_rank' => '":title" ได้รับการจัดอันดับ', 79 - 'beatmapset_rank_compact' => 'บีตแม็ปได้รับการจัดอันดับ', 79 + 'beatmapset_rank_compact' => 'บีทแมพได้รับการจัดอันดับ', 80 80 'beatmapset_remove_from_loved' => '":title" ได้ถูกนำออกจากรักเลย', 81 - 'beatmapset_remove_from_loved_compact' => 'บีตแม็ปได้ถูกนำออกจากชื่นชอบ', 81 + 'beatmapset_remove_from_loved_compact' => 'บีทแมพได้ถูกนำออกจาก Loved', 82 82 'beatmapset_reset_nominations' => 'การเสนอชื่อ ":title" ถูกรีเซ็ต', 83 83 'beatmapset_reset_nominations_compact' => 'การเสนอชื่อถูกรีเซ็ท', 84 84 ], ··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'ฟอรั่ม PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited ข้อความที่ยังไม่ได้อ่าน |:count_delimited ข้อความทั้งหมดที่ยังไม่ได้อ่าน', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 - '_' => 'บีตแม็ปใหม่', 158 + '_' => 'บีทแมพใหม่', 168 159 169 - 'user_beatmapset_new' => 'บีตแม็ปใหม่ ":title" โดย :username', 170 - 'user_beatmapset_new_compact' => 'บีตแม็ปใหม่ ":title"', 171 - 'user_beatmapset_new_group' => 'บีตแม็ปใหม่โดย :username', 160 + 'user_beatmapset_new' => 'บีทแมพใหม่ ":title" โดย :username', 161 + 'user_beatmapset_new_compact' => 'บีทแมพใหม่ ":title"', 162 + 'user_beatmapset_new_group' => 'บีทแมพใหม่โดย :username', 172 163 173 - 'user_beatmapset_revive' => 'บีตแม็ป ":title" ถูกกู้คืนแล้วโดย :username', 174 - 'user_beatmapset_revive_compact' => 'บีตแม็ป ":title" ถูกกู้คืนแล้ว', 164 + 'user_beatmapset_revive' => 'บีทแมพ ":title" ถูกกู้คืนแล้วโดย :username', 165 + 'user_beatmapset_revive_compact' => 'บีทแมพ ":title" ถูกกู้คืนแล้ว', 175 166 ], 176 167 ], 177 168 ··· 190 181 'mail' => [ 191 182 'beatmapset' => [ 192 183 'beatmap_owner_change' => [ 193 - 'beatmap_owner_change' => 'ตอนนี้คุณเป็นแขกของบีตแม็ป ":title"', 184 + 'beatmap_owner_change' => 'ตอนนี้คุณเป็นแขกของบีทแมพ ":title"', 194 185 ], 195 186 196 187 'beatmapset_discussion' => [ ··· 214 205 ], 215 206 216 207 'comment' => [ 217 - 'comment_new' => 'บีตแม็ป ":title" มีความคิดเห็นใหม่', 208 + 'comment_new' => ' บีทแมพ ":title" มีความคิดเห็นใหม่', 218 209 ], 219 210 ], 220 211 ··· 253 244 ], 254 245 255 246 'user_beatmapset_new' => [ 256 - 'user_beatmapset_new' => ':username ได้สร้างบีตแม็ปใหม่', 257 - 'user_beatmapset_revive' => ':username ได้กู้คืนบีตแม็ปแล้ว', 247 + 'user_beatmapset_new' => ':username ได้สร้างบีทแมพใหม่', 248 + 'user_beatmapset_revive' => ':username ได้กู้คืนบีทแมพแล้ว', 258 249 ], 259 250 ], 260 251 ],
+6 -6
resources/lang/th/page_title.php
··· 41 41 '_' => 'การสนทนาเกี่ยวกับ Beatmap', 42 42 ], 43 43 'beatmap_packs_controller' => [ 44 - '_' => 'แพ็คบีตแม็ป', 44 + '_' => 'แพ็คบีทแมพ', 45 45 ], 46 46 'beatmapset_discussion_votes_controller' => [ 47 - '_' => 'โหวตการสนทนาบีตแม็ป', 47 + '_' => 'โหวตการสนทนาบีทแมพ', 48 48 ], 49 49 'beatmapset_events_controller' => [ 50 - '_' => 'ประวัติบีตแม็ป', 50 + '_' => 'ประวัติบีทแมพ', 51 51 ], 52 52 'beatmapsets_controller' => [ 53 - 'discussion' => 'การสนทนาเกี่ยวกับบีตแม็ป', 54 - 'index' => 'รายการบีตแม็ป', 55 - 'show' => 'ข้อมูลบีตแม็ป', 53 + 'discussion' => 'การสนทนาเกี่ยวกับบีทแมพ', 54 + 'index' => 'รายการบีทแมพ', 55 + 'show' => 'ข้อมูลบีทแมพ', 56 56 ], 57 57 'changelog_controller' => [ 58 58 '_' => 'การเปลี่ยนแปลง',
+7
resources/lang/th/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'โดดเด่น', 22 28 'country' => 'ประเทศ', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'โหมดผู้เล่นหลายคน', 24 31 'performance' => 'ประสิทธิภาพ', 25 32 'score' => 'คะแนน',
+1 -1
resources/lang/th/report.php
··· 6 6 return [ 7 7 'beatmapset' => [ 8 8 'button' => 'รายงาน', 9 - 'title' => 'คุณต้องการรายงานบีตแม็ปของ :username หรือไม่?', 9 + 'title' => 'คุณต้องการรายงานบีทแมพของ :username หรือไม่?', 10 10 ], 11 11 12 12 'beatmapset_discussion_post' => [
+14 -14
resources/lang/th/users.php
··· 223 223 ], 224 224 'beatmaps' => [ 225 225 'by_artist' => 'โดย :artist', 226 - 'title' => 'บีตแม็ป', 226 + 'title' => 'บีทแมพ', 227 227 228 228 'favourite' => [ 229 - 'title' => 'บีตแม็ปรายการโปรด', 229 + 'title' => 'บีทแมพที่ชื่นชอบ', 230 230 ], 231 231 'graveyard' => [ 232 - 'title' => 'สุสานบีตแม็ป', 232 + 'title' => 'สุสานบีทแมพ', 233 233 ], 234 234 'guest' => [ 235 - 'title' => 'แขกผู้ที่มีส่วนร่วมบีตแม็ป', 235 + 'title' => 'แขกผู้ที่มีส่วนร่วมบีทแมพ', 236 236 ], 237 237 'loved' => [ 238 - 'title' => 'บีตแม็ปที่ชื่นชอบ', 238 + 'title' => 'บีทแมพที่ Loved', 239 239 ], 240 240 'nominated' => [ 241 - 'title' => 'เสนอชื่อเข้าชิงอันดับบีตแม็ป', 241 + 'title' => 'บีทแมพที่ถูกเสนอชื่อแล้ว', 242 242 ], 243 243 'pending' => [ 244 - 'title' => 'บีตแม็ปที่กำลังทำ', 244 + 'title' => 'บีทแมพที่กำลังทำ', 245 245 ], 246 246 'ranked' => [ 247 - 'title' => 'บีตแม็ปที่จัดอันดับแล้ว', 247 + 'title' => 'บีทแมพที่จัดอันดับแล้ว', 248 248 ], 249 249 ], 250 250 'discussions' => [ ··· 266 266 ], 267 267 'most_played' => [ 268 268 'count' => 'จำนวนครั้งที่เล่น', 269 - 'title' => 'บีตแม็ปที่เล่นมากที่สุด', 269 + 'title' => 'บีทแมพที่เล่นมากที่สุด', 270 270 ], 271 271 'recent_plays' => [ 272 272 'accuracy' => 'ความแม่นยำ: :percentage', ··· 322 322 ], 323 323 324 324 'total_info' => [ 325 - '_' => 'ขึ้นอยู่กับการดูแลบีตแม็ปของเจ้าของบีตแม็ป ดูรายละเอียดเพิ่มเติมที่นี่ :link', 325 + '_' => 'ขึ้นอยู่กับการดูแลบีทแมพของเจ้าของบีทแมพ ดูรายละเอียดเพิ่มเติมที่นี่ :link', 326 326 'link' => 'หน้านี้', 327 327 ], 328 328 ], ··· 350 350 ], 351 351 'top_ranks' => [ 352 352 'download_replay' => 'ดาวน์โหลดรีเพลย์', 353 - 'not_ranked' => 'เฉพาะบีตแม็ปที่จัดอันดับแล้วเท่านั้นที่จะให้ pp', 353 + 'not_ranked' => 'เฉพาะบีทแมพที่จัดอันดับแล้วเท่านั้นที่จะให้ pp', 354 354 'pp_weight' => 'น้ำหนัก :percentage', 355 355 'view_details' => 'ดูรายละเอียดเพิ่มเติม', 356 356 'title' => 'อันดับ', ··· 453 453 'total_hits' => 'Hit รวม', 454 454 'total_score' => 'คะแนนรวมทั้งหมด', 455 455 // modding stats 456 - 'graveyard_beatmapset_count' => 'สุสานบีตแม็ป', 457 - 'loved_beatmapset_count' => 'บีตแม็ปที่ชื่นชอบ', 456 + 'graveyard_beatmapset_count' => 'สุสานบีทแมพ', 457 + 'loved_beatmapset_count' => 'บีทแมพที่ Loved', 458 458 'pending_beatmapset_count' => 'บีทเเมพที่กำลังทำ', 459 - 'ranked_beatmapset_count' => 'บีตแม็ปที่จัดอันดับแล้ว', 459 + 'ranked_beatmapset_count' => 'บีทแมพที่จัดอันดับแล้ว', 460 460 ], 461 461 ], 462 462
+1
resources/lang/tr/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Sadece skor sahibi skoru sabitleyebilir.', 175 176 'too_many' => 'Çok fazla skor sabitlendi.', 176 177 ],
-9
resources/lang/tr/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Legacy Forum PM', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited okunmamış mesaj.|:count_delimited okunmamış mesaj', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Yeni beatmap',
+7
resources/lang/tr/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'Öne Çıkanlar', 22 28 'country' => 'Ülke', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'çok oyunculu', 24 31 'performance' => 'Performans', 25 32 'score' => 'Skor',
+1
resources/lang/uk/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Лише власник результату може його закріпити.', 175 176 'too_many' => 'Закріплено надто багато результатів.', 176 177 ],
-9
resources/lang/uk/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => 'Вхідні повідомлення старого форуму', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited непрочитане повідомлення.|:count_delimited непрочитані повідомлення.', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => 'Нова бітмапа',
+7
resources/lang/uk/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'чарти', 22 28 'country' => 'країни', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'мультиплеєр', 24 31 'performance' => 'продуктивність', 25 32 'score' => 'очки',
+1
resources/lang/vi/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => 'Chỉ có người sở hữu có thể ghim điểm.', 175 176 'too_many' => 'Ghim quá nhiều điểm.', 176 177 ],
-9
resources/lang/vi/notifications.php
··· 154 154 ], 155 155 ], 156 156 157 - 'legacy_pm' => [ 158 - '_' => 'Diễn đàn kế thừa PM', 159 - 160 - 'legacy_pm' => [ 161 - '_' => '', 162 - 'legacy_pm' => ':count_delimited tin nhắn chưa đọc|:count_delimited tin nhắn chưa đọc', 163 - ], 164 - ], 165 - 166 157 'user' => [ 167 158 'user_beatmapset_new' => [ 168 159 '_' => 'Beatmap mới',
+7
resources/lang/vi/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => 'tiêu điểm', 22 28 'country' => 'Quốc gia', 29 + 'kudosu' => '', 23 30 'multiplayer' => 'nhiều người chơi', 24 31 'performance' => 'thành tích', 25 32 'score' => 'số điểm',
+1
resources/lang/zh-tw/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '只有擁有者才可置頂成績。', 175 176 'too_many' => '置頂過多成績。', 176 177 ],
-9
resources/lang/zh-tw/notifications.php
··· 153 153 ], 154 154 ], 155 155 156 - 'legacy_pm' => [ 157 - '_' => '舊論壇私訊', 158 - 159 - 'legacy_pm' => [ 160 - '_' => '', 161 - 'legacy_pm' => ':count_delimited 則未讀訊息', 162 - ], 163 - ], 164 - 165 156 'user' => [ 166 157 'user_beatmapset_new' => [ 167 158 '_' => '新圖譜',
+7
resources/lang/zh-tw/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => '月賽', 22 28 'country' => '國家', 29 + 'kudosu' => '', 23 30 'multiplayer' => '多人遊戲', 24 31 'performance' => '成績', 25 32 'score' => '總分',
+1
resources/lang/zh/authorization.php
··· 171 171 172 172 'score' => [ 173 173 'pin' => [ 174 + 'disabled_type' => "", 174 175 'not_owner' => '只有获得此成绩的玩家才可以置顶它。', 175 176 'too_many' => '已置顶的成绩过多', 176 177 ],
-9
resources/lang/zh/notifications.php
··· 155 155 ], 156 156 ], 157 157 158 - 'legacy_pm' => [ 159 - '_' => '旧论坛私信', 160 - 161 - 'legacy_pm' => [ 162 - '_' => '', 163 - 'legacy_pm' => ':count_delimited 条未读消息', 164 - ], 165 - ], 166 - 167 158 'user' => [ 168 159 'user_beatmapset_new' => [ 169 160 '_' => '新谱面',
+7
resources/lang/zh/rankings.php
··· 17 17 ], 18 18 ], 19 19 20 + 'kudosu' => [ 21 + 'total' => '', 22 + 'available' => '', 23 + 'used' => '', 24 + ], 25 + 20 26 'type' => [ 21 27 'charts' => '高光', 22 28 'country' => '国家/地区', 29 + 'kudosu' => '', 23 30 'multiplayer' => '多人游戏', 24 31 'performance' => '表现', 25 32 'score' => '总分',
+43
resources/views/accounts/_edit_country.blade.php
··· 1 + {{-- 2 + Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 3 + See the LICENCE file in the repository root for full licence text. 4 + --}} 5 + @php 6 + use App\Libraries\User\CountryChangeTarget; 7 + use App\Models\Country; 8 + 9 + $countryChangeTarget = CountryChangeTarget::get($user); 10 + @endphp 11 + <div class="account-edit-entry account-edit-entry--read-only"> 12 + <div class="account-edit-entry__label account-edit-entry__label--top-pinned"> 13 + {{ osu_trans('accounts.edit.profile.country') }} 14 + </div> 15 + <div> 16 + <p> 17 + @include('objects._flag_country', [ 18 + 'countryCode' => $user->country_acronym, 19 + 'countryName' => null, 20 + 'modifiers' => 'wiki', 21 + ]) 22 + {{ $user->country->name }} 23 + </p> 24 + @if ($countryChangeTarget !== null) 25 + <p> 26 + {!! osu_trans('accounts.edit.profile.country_change._', [ 27 + 'update_link' => tag( 28 + 'a', 29 + [ 30 + 'data-confirm' => osu_trans('common.confirmation'), 31 + 'data-method' => 'PUT', 32 + 'data-remote' => '1', 33 + 'href' => route('account.country', ['country_acronym' => $countryChangeTarget]), 34 + ], 35 + osu_trans('accounts.edit.profile.country_change.update_link', [ 36 + 'country' => Country::find($countryChangeTarget)->name, 37 + ]), 38 + ), 39 + ]) !!} 40 + </p> 41 + @endif 42 + </div> 43 + </div>
+30 -28
resources/views/accounts/_edit_notifications.blade.php
··· 67 67 <div class="account-edit__input-group"> 68 68 @foreach (UserNotificationOption::BEATMAPSET_DISQUALIFIABLE_NOTIFICATIONS as $notificationType) 69 69 <div class="account-edit-entry account-edit-entry--no-label"> 70 - <div class="account-edit-entry__checkboxes-label"> 71 - {{ osu_trans("accounts.notifications.$notificationType") }} 72 - </div> 73 - <form 74 - class="account-edit-entry__checkboxes js-account-edit" 75 - data-account-edit-auto-submit="1" 76 - data-account-edit-type="array" 77 - data-url="{{ route('account.notification-options') }}" 78 - data-field="{{ "user_notification_option[{$notificationType}][details][modes]" }}" 79 - > 80 - @php 81 - $modes = $notificationOptions[$notificationType]->details['modes'] ?? []; 82 - @endphp 83 - @foreach (App\Models\Beatmap::MODES as $key => $_value) 84 - <label class="account-edit-entry__checkbox account-edit-entry__checkbox--inline"> 85 - @include('objects._switch', ['locals' => [ 86 - 'checked' => in_array($key, $modes, true), 87 - 'value' => $key, 88 - ]]) 70 + <div> 71 + <div class="account-edit-entry__checkboxes-label"> 72 + {{ osu_trans("accounts.notifications.$notificationType") }} 73 + </div> 74 + <form 75 + class="account-edit-entry__checkboxes js-account-edit" 76 + data-account-edit-auto-submit="1" 77 + data-account-edit-type="array" 78 + data-url="{{ route('account.notification-options') }}" 79 + data-field="{{ "user_notification_option[{$notificationType}][details][modes]" }}" 80 + > 81 + @php 82 + $modes = $notificationOptions[$notificationType]->details['modes'] ?? []; 83 + @endphp 84 + @foreach (App\Models\Beatmap::MODES as $key => $_value) 85 + <label class="account-edit-entry__checkbox account-edit-entry__checkbox--inline"> 86 + @include('objects._switch', ['locals' => [ 87 + 'checked' => in_array($key, $modes, true), 88 + 'value' => $key, 89 + ]]) 89 90 90 - <span class="account-edit-entry__checkbox-label"> 91 - {{ osu_trans("beatmaps.mode.{$key}") }} 92 - </span> 93 - </label> 94 - @endforeach 91 + <span class="account-edit-entry__checkbox-label"> 92 + {{ osu_trans("beatmaps.mode.{$key}") }} 93 + </span> 94 + </label> 95 + @endforeach 95 96 96 - <div class="account-edit-entry__checkboxes-status"> 97 - @include('accounts._edit_entry_status') 98 - </div> 99 - </form> 97 + <div class="account-edit-entry__checkboxes-status"> 98 + @include('accounts._edit_entry_status') 99 + </div> 100 + </form> 101 + </div> 100 102 </div> 101 103 @endforeach 102 104 </div>
+42 -40
resources/views/accounts/_edit_options.blade.php
··· 15 15 <div class="account-edit__input-groups"> 16 16 <div class="account-edit__input-group"> 17 17 <div class="account-edit-entry account-edit-entry--no-label"> 18 - <div class="account-edit-entry__checkboxes-label"> 19 - {{ osu_trans('accounts.options.beatmapset_download._') }} 20 - </div> 21 - <form 22 - class="account-edit-entry__checkboxes account-edit-entry__checkboxes--vertical js-account-edit" 23 - data-account-edit-auto-submit="1" 24 - data-account-edit-type="radio" 25 - data-url="{{ route('account.options') }}" 26 - data-field="user_profile_customization[beatmapset_download]" 27 - > 28 - @php 29 - $statusIsRendered = false; 30 - @endphp 31 - @foreach (App\Models\UserProfileCustomization::BEATMAPSET_DOWNLOAD as $name) 32 - @if ($name === 'direct' && !auth()->user()->isSupporter()) 33 - @continue 34 - @endif 35 - <label 36 - class="account-edit-entry__checkbox account-edit-entry__checkbox--inline" 37 - > 38 - @include('objects._switch', ['locals' => [ 39 - 'checked' => $customization->beatmapset_download === $name, 40 - 'name' => 'user_profile_customization[beatmapset_download]', 41 - 'type' => 'radio', 42 - 'value' => $name, 43 - ]]) 18 + <div> 19 + <div class="account-edit-entry__checkboxes-label"> 20 + {{ osu_trans('accounts.options.beatmapset_download._') }} 21 + </div> 22 + <form 23 + class="account-edit-entry__checkboxes account-edit-entry__checkboxes--vertical js-account-edit" 24 + data-account-edit-auto-submit="1" 25 + data-account-edit-type="radio" 26 + data-url="{{ route('account.options') }}" 27 + data-field="user_profile_customization[beatmapset_download]" 28 + > 29 + @php 30 + $statusIsRendered = false; 31 + @endphp 32 + @foreach (App\Models\UserProfileCustomization::BEATMAPSET_DOWNLOAD as $name) 33 + @if ($name === 'direct' && !auth()->user()->isSupporter()) 34 + @continue 35 + @endif 36 + <label 37 + class="account-edit-entry__checkbox account-edit-entry__checkbox--inline" 38 + > 39 + @include('objects._switch', ['locals' => [ 40 + 'checked' => $customization->beatmapset_download === $name, 41 + 'name' => 'user_profile_customization[beatmapset_download]', 42 + 'type' => 'radio', 43 + 'value' => $name, 44 + ]]) 44 45 45 - <span class="account-edit-entry__checkbox-label"> 46 - {{ osu_trans("accounts.options.beatmapset_download.{$name}") }} 47 - </span> 46 + <span class="account-edit-entry__checkbox-label"> 47 + {{ osu_trans("accounts.options.beatmapset_download.{$name}") }} 48 + </span> 48 49 49 - @if (!$statusIsRendered) 50 - <div class="account-edit-entry__checkbox-status"> 51 - @include('accounts._edit_entry_status') 52 - </div> 53 - @php 54 - $statusIsRendered = true; 55 - @endphp 56 - @endif 57 - </label> 58 - @endforeach 59 - </form> 50 + @if (!$statusIsRendered) 51 + <div class="account-edit-entry__checkbox-status"> 52 + @include('accounts._edit_entry_status') 53 + </div> 54 + @php 55 + $statusIsRendered = true; 56 + @endphp 57 + @endif 58 + </label> 59 + @endforeach 60 + </form> 61 + </div> 60 62 </div> 61 63 </div> 62 64
+10 -4
resources/views/accounts/edit.blade.php
··· 2 2 Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 3 3 See the LICENCE file in the repository root for full licence text. 4 4 --}} 5 + @php 6 + $user = Auth::user(); 7 + $isSilenced = $user->isSilenced(); 8 + @endphp 9 + 5 10 @extends('master', ['titlePrepend' => osu_trans('accounts.edit.title_compact')]) 6 11 7 12 @section('content') 8 - @if (Auth::user()->isSilenced() && !Auth::user()->isRestricted()) 13 + @if ($isSilenced && !$user->isRestricted()) 9 14 @include('objects._notification_banner', [ 10 15 'type' => 'alert', 11 16 'title' => osu_trans('users.silenced_banner.title'), ··· 30 35 {{ osu_trans('accounts.edit.username') }} 31 36 </div> 32 37 <div class="account-edit-entry__input"> 33 - {{ Auth::user()->username }} 38 + {{ $user->username }} 34 39 </div> 35 40 36 41 <div class="account-edit-entry__button"> ··· 47 52 </a> 48 53 </div> 49 54 </div> 55 + @include('accounts._edit_country') 50 56 </div> 51 57 <div class="account-edit__input-group"> 52 58 @include('accounts._edit_entry_simple', ['field' => 'user_from']) ··· 89 95 90 96 <label 91 97 class="btn-osu-big btn-osu-big--account-edit" 92 - @if (Auth::user()->isSilenced()) 98 + @if ($isSilenced) 93 99 disabled 94 100 @endif 95 101 > ··· 108 114 type="file" 109 115 name="avatar_file" 110 116 data-url="{{ route('account.avatar') }}" 111 - @if (Auth::user()->isSilenced()) 117 + @if ($isSilenced) 112 118 disabled 113 119 @endif 114 120 >
+22 -22
resources/views/docs/_structures/beatmapset.md
··· 2 2 3 3 Represents a beatmapset. This extends [BeatmapsetCompact](#beatmapsetcompact) with additional attributes. 4 4 5 - Field | Type | Description 6 - ------------------------------ | ------------------------ | ----------------------------------------------------------------------- 7 - availability.download_disabled | boolean | | 8 - availability.more_information | string? | | 9 - bpm | float | | 10 - can_be_hyped | boolean | | 11 - creator | string | Username of the mapper at the time of beatmapset creation. 12 - deleted_at | string? | | 13 - discussion_locked | boolean | | 14 - hype.current | integer | | 15 - hype.required | integer | | 16 - is_scoreable | boolean | | 17 - last_updated | [Timestamp](#timestamp) | | 18 - legacy_thread_url | string? | | 19 - nominations.current | integer | | 20 - nominations.required | integer | | 21 - ranked | integer | See [Rank status](#beatmapset-rank-status) for list of possible values. 22 - ranked_date | [Timestamp](#timestamp)? | | 23 - source | string | | 24 - storyboard | boolean | | 25 - submitted_date | [Timestamp](#timestamp)? | | 26 - tags | string | | 5 + Field | Type | Description 6 + ------------------------------ | ---------------------------- | ----------------------------------------------------------------------- 7 + availability.download_disabled | boolean | | 8 + availability.more_information | string? | | 9 + bpm | float | | 10 + can_be_hyped | boolean | | 11 + deleted_at | string? | | 12 + discussion_enabled | boolean | Deprecated, all beatmapsets now have discussion enabled. | 13 + discussion_locked | boolean | | 14 + hype.current | integer | | 15 + hype.required | integer | | 16 + is_scoreable | boolean | | 17 + last_updated | [Timestamp](#timestamp) | | 18 + legacy_thread_url | string? | | 19 + nominations_summary.current | integer | | 20 + nominations_summary.required | integer | | 21 + ranked | integer | See [Rank status](#beatmapset-rank-status) for list of possible values. 22 + ranked_date | [Timestamp](#timestamp)? | | 23 + source | string | | 24 + storyboard | boolean | | 25 + submitted_date | [Timestamp](#timestamp)? | | 26 + tags | string | | 27 27 28 28 The following attributes are always included as well: 29 29
+21 -17
resources/views/docs/_structures/beatmapset_compact.md
··· 11 11 favourite_count | number | | 12 12 id | number | | 13 13 nsfw | boolean | | 14 + offset | number | | 14 15 play_count | number | | 15 16 preview_url | string | | 16 17 source | string | | 17 18 status | string | | 19 + spotlight | boolean | | 18 20 title | string | | 19 21 title_unicode | string | | 20 22 user_id | number | | ··· 22 24 23 25 Those fields are optional. 24 26 25 - Field | Type | Description 26 - ----------------------- | --------------------- | ----------- 27 - beatmaps | [Beatmap](#beatmap)[] | | 28 - converts | | | 29 - current_user_attributes | | | 30 - description | | | 31 - discussions | | | 32 - events | | | 33 - genre | | | 34 - has_favourited | boolean | | 35 - language | | | 36 - nominations | | | 37 - pack_tags | string[] | | 38 - ratings | | | 39 - recent_favourites | | | 40 - related_users | | | 41 - user | | | 27 + Field | Type | Description 28 + ----------------------- | ---------------------------- | ----------- 29 + beatmaps | [Beatmap](#beatmap)[] | | 30 + converts | | | 31 + current_nominations | [Nomination](#nomination)[] | | 32 + current_user_attributes | | | 33 + description | | | 34 + discussions | | | 35 + events | | | 36 + genre | | | 37 + has_favourited | boolean | | 38 + language | | | 39 + nominations | | | 40 + pack_tags | string[] | | 41 + ratings | | | 42 + recent_favourites | | | 43 + related_users | | | 44 + user | | | 45 + track_id | number | | 42 46 43 47 <div id="beatmapsetcompact-covers" data-unique="beatmapsetcompact-covers"></div> 44 48
+1
resources/views/docs/_structures/build.md
··· 24 24 update_stream | [UpdateStream](#updatestream)? 25 25 users | number 26 26 version | string? 27 + youtube_id | string? 27 28 28 29 ### Optional Attributes 29 30
+1
resources/views/docs/_structures/chat_channel.md
··· 31 31 description | string? | | 32 32 icon | string? | display icon for the channel 33 33 type | [ChannelType](#channeltype) | type of channel 34 + message_length_limit | number | | 34 35 moderated | boolean | user can't send message when the value is `true` 35 36 uuid | string? | value from requests that is relayed back to the sender. 36 37
+1 -1
resources/views/docs/_structures/comment.md
··· 20 20 } 21 21 ``` 22 22 23 - Represents an single comment. 23 + Represents a single comment. 24 24 25 25 Field | Type | Description 26 26 ---------------- | ---------- | ------------------
+8
resources/views/docs/_structures/nomination.md
··· 1 + ## Nomination 2 + 3 + Field | Type 4 + -----------------|----- 5 + beatmapset_id | number 6 + rulesets | [GameMode](#gamemode)[] 7 + reset | boolean 8 + user_id | number
+3
resources/views/docs/_structures/user_compact.md
··· 48 48 country | | 49 49 cover | | 50 50 favourite_beatmapset_count | number 51 + follow_user_mapping | number[] 51 52 follower_count | number 52 53 friends | | 53 54 graveyard_beatmapset_count | number 54 55 groups | [UserGroup](#usergroup)[] 56 + guest_beatmapset_count | number 55 57 is_restricted | boolean? 56 58 loved_beatmapset_count | number 59 + mapping_follower_count | number 57 60 monthly_playcounts | [UserMonthlyPlaycount](#usermonthlyplaycount)[] 58 61 page | | 59 62 pending_beatmapset_count | |
+3
resources/views/docs/_structures/user_statistics.md
··· 61 61 count_300 | number | | 62 62 count_50 | number | | 63 63 count_miss | number | | 64 + country_rank | number? | Current country rank according to pp. | 64 65 grade_counts.a | number | Number of A ranked scores. 65 66 grade_counts.s | number | Number of S ranked scores. 66 67 grade_counts.sh | number | Number of Silver S ranked scores. ··· 74 75 play_count | number | Number of maps played. 75 76 play_time | number | Cumulative time played. 76 77 pp | number | Performance points 78 + pp_exp | number | Experimental (lazer) performance points 77 79 global_rank | number? | Current rank according to pp. 80 + global_rank_exp | number? | Current rank according to experimental (lazer) pp. 78 81 ranked_score | number | Current ranked score. 79 82 replays_watched_by_others | number | Number of replays watched by other users. 80 83 total_hits | number | Total number of hits.
+5 -3
resources/views/forum/topics/create.blade.php
··· 47 47 </label> 48 48 </div> 49 49 50 - <div class="forum-topic-toolbar__item u-relative"> 51 - @include('forum.topics._cover_editor') 52 - </div> 50 + @if (priv_check('ForumTopicCoverStore', $forum)->can()) 51 + <div class="forum-topic-toolbar__item u-relative"> 52 + @include('forum.topics._cover_editor') 53 + </div> 54 + @endif 53 55 </div> 54 56 55 57 {{-- inlined style to work with jquery's slide animation --}}
+9 -4
resources/views/home/user.blade.php
··· 2 2 Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 3 3 See the LICENCE file in the repository root for full licence text. 4 4 --}} 5 + @php 6 + use App\Models\NewsPost; 7 + 8 + $newsPostLargePreviews = NewsPost::LANDING_LIMIT; 9 + @endphp 5 10 @extends('master') 6 11 7 12 @section('content') ··· 13 18 <h2 class="user-home__news-title">{{ osu_trans('home.user.news.title') }}</h2> 14 19 15 20 @foreach ($news as $post) 16 - @if ($loop->iteration > 3) 21 + @if ($loop->iteration > $newsPostLargePreviews) 17 22 @break 18 23 @endif 19 24 20 25 @include('home._user_news_post_preview', ['post' => $post, 'collapsed' => false]) 21 26 @endforeach 22 27 23 - @if (count($news) > 3) 28 + @if (count($news) > $newsPostLargePreviews) 24 29 <div class="user-home__news-posts-group"> 25 30 @foreach ($news as $post) 26 - @if ($loop->iteration <= 3) 31 + @if ($loop->iteration <= $newsPostLargePreviews) 27 32 @continue 28 33 @endif 29 34 ··· 32 37 </div> 33 38 @endif 34 39 35 - @if (count($news) > App\Models\NewsPost::DASHBOARD_LIMIT) 40 + @if (count($news) > NewsPost::DASHBOARD_LIMIT) 36 41 <a 37 42 href="{{ route('news.index') }}" 38 43 class="user-home__news-posts-group user-home__news-posts-group--more"
+1 -1
resources/views/layout/popup-container.blade.php
··· 3 3 See the LICENCE file in the repository root for full licence text. 4 4 --}} 5 5 @php 6 - $popup = Session::get('popup'); 6 + $popup = Session('popup'); 7 7 @endphp 8 8 <div id="popup-container"> 9 9 <div class="alert alert-dismissable popup-clone col-md-6 col-md-offset-3 text-center" style="display: none">
+2 -2
resources/views/objects/_flag_country.blade.php
··· 2 2 Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 3 3 See the LICENCE file in the repository root for full licence text. 4 4 --}} 5 - <div class="{{ class_with_modifiers('flag-country', $modifiers ?? []) }}" 5 + <span class="{{ class_with_modifiers('flag-country', $modifiers ?? []) }}" 6 6 @if (isset($countryName)) 7 7 title="{{ $countryName }}" 8 8 @endif 9 9 style="background-image: url('{{ flag_url($countryCode) }}');" 10 - ></div> 10 + ></span>
+6 -3
resources/views/rankings/kudosu.blade.php
··· 2 2 Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 3 3 See the LICENCE file in the repository root for full licence text. 4 4 --}} 5 + @php 6 + $firstScoreRank = $scores->firstItem(); 7 + @endphp 5 8 @extends('rankings.index', [ 6 9 'hasFilter' => false, 7 10 'hasMode' => false, 8 - 'hasPager' => false, 11 + 'hasPager' => true, 9 12 'type' => 'kudosu', 10 13 ]) 11 14 ··· 27 30 </tr> 28 31 </thead> 29 32 <tbody> 30 - @foreach ($users as $index => $user) 33 + @foreach ($scores as $index => $user) 31 34 <tr class="{{ class_with_modifiers('ranking-page-table__row', ['inactive' => !$user->isActive()]) }}"> 32 35 <td class="ranking-page-table__column ranking-page-table__column--rank"> 33 - #{{ i18n_number_format($index + 1) }} 36 + #{{ i18n_number_format($index + $firstScoreRank) }} 34 37 </td> 35 38 <td class="ranking-page-table__column"> 36 39 <div class="ranking-page-table__user-link">
+1
routes/web.php
··· 204 204 // Reference: https://bugs.php.net/bug.php?id=55815 205 205 // Note that hhvm behaves differently (the same as POST). 206 206 Route::post('avatar', 'AccountController@avatar')->name('avatar'); 207 + Route::put('country', 'AccountController@updateCountry')->name('country'); 207 208 Route::post('cover', 'AccountController@cover')->name('cover'); 208 209 Route::put('email', 'AccountController@updateEmail')->name('email'); 209 210 Route::put('notification-options', 'AccountController@updateNotificationOptions')->name('notification-options');
-2
tests/Browser/SanityTest.php
··· 360 360 361 361 // TODO: add additional logic for certain routes to re-run tests per game mode, per user score type, etc 362 362 $this->browse(function (Browser $browser) use ($route, $type, $url) { 363 - static::resetSession($browser); 364 - 365 363 try { 366 364 if ($type === 'user') { 367 365 $browser->loginAs(self::$scaffolding['user']);
+32
tests/Controllers/AccountControllerTest.php
··· 9 9 10 10 use App\Mail\UserEmailUpdated; 11 11 use App\Mail\UserPasswordUpdated; 12 + use App\Models\Country; 12 13 use App\Models\User; 13 14 use App\Models\UserProfileCustomization; 14 15 use App\Models\WeakPassword; 16 + use Database\Factories\UserFactory; 15 17 use Hash; 16 18 use Mail; 17 19 use Tests\TestCase; ··· 62 64 'order' => $newOrderWithInvalid, 63 65 ]) 64 66 ->assertJsonFragment(['profile_order' => $newOrder]); 67 + } 68 + 69 + /** 70 + * @dataProvider dataProviderForUpdateCountry 71 + * 72 + * More complete tests are done through CountryChange and CountryChangeTarget. 73 + */ 74 + public function testUpdateCountry(string $historyCountry, string $targetCountry, bool $success): void 75 + { 76 + $user = $this->user(); 77 + foreach (array_unique([$historyCountry, $targetCountry]) as $country) { 78 + Country::factory()->create(['acronym' => $country]); 79 + } 80 + UserFactory::createRecentCountryHistory($user, $historyCountry, null); 81 + 82 + $resultCountry = $success ? $targetCountry : $user->country_acronym; 83 + 84 + $this->actingAsVerified($user) 85 + ->json('PUT', route('account.country', ['country_acronym' => $targetCountry])) 86 + ->assertStatus($success ? 200 : 403); 87 + 88 + $this->assertSame($user->fresh()->country_acronym, $resultCountry); 65 89 } 66 90 67 91 public function testUpdateEmail() ··· 188 212 ], 189 213 ]) 190 214 ->assertStatus(422); 215 + } 216 + 217 + public function dataProviderForUpdateCountry(): array 218 + { 219 + return [ 220 + ['_A', '_A', true], 221 + ['_B', '_A', false], 222 + ]; 191 223 } 192 224 193 225 protected function setUp(): void
+9
tests/DuskTestCase.php
··· 71 71 72 72 return $driver; 73 73 } 74 + 75 + protected function setUp(): void 76 + { 77 + parent::setUp(); 78 + 79 + foreach (static::$browsers as $browser) { 80 + static::resetSession($browser); 81 + } 82 + } 74 83 }
+4 -2
tests/Libraries/Search/BeatmapsetQueryParserTest.php
··· 50 50 ['ranked=2018/05', ['keywords' => null, 'options' => ['ranked' => ['gte' => '2018-05-01T00:00:00+00:00', 'lt' => '2018-06-01T00:00:00+00:00']]]], 51 51 ['ranked=2018.05.01', ['keywords' => null, 'options' => ['ranked' => ['gte' => '2018-05-01T00:00:00+00:00', 'lt' => '2018-05-02T00:00:00+00:00']]]], 52 52 ['ranked>2018/05/01', ['keywords' => null, 'options' => ['ranked' => ['gte' => '2018-05-02T00:00:00+00:00']]]], 53 - ['ranked>="2020-07-21 12:30:30 +09:00"', ['keywords' => null, 'options' => ['ranked' => ['gte' => '2020-07-21T12:30:30+09:00']]]], 54 - ['ranked="2020-07-21 12:30:30 +09:00"', ['keywords' => null, 'options' => ['ranked' => ['gte' => '2020-07-21T12:30:30+09:00', 'lt' => '2020-07-21T12:30:31+09:00']]]], 53 + ['ranked>="2020-07-21 12:30:30 +09:00"', ['keywords' => null, 'options' => ['ranked' => ['gte' => '2020-07-21T03:30:30+00:00']]]], 54 + ['ranked="2020-07-21 12:30:30 +09:00"', ['keywords' => null, 'options' => ['ranked' => ['gte' => '2020-07-21T03:30:30+00:00', 'lt' => '2020-07-21T03:30:31+00:00']]]], 55 55 ['ranked="invalid date format"', ['keywords' => 'ranked="invalid date format"', 'options' => []]], 56 56 57 57 // multiple options ··· 98 98 ['bpm=bad', ['keywords' => 'bpm=bad', 'options' => []]], 99 99 ['divisor<nah', ['keywords' => 'divisor<nah', 'options' => []]], 100 100 ['status=noidea', ['keywords' => 'status=noidea', 'options' => []]], 101 + ['status=l', ['keywords' => null, 'options' => ['status' => ['gte' => Beatmapset::STATES['loved'], 'lte' => Beatmapset::STATES['loved']]]]], 102 + ['status=lo', ['keywords' => null, 'options' => ['status' => ['gte' => Beatmapset::STATES['loved'], 'lte' => Beatmapset::STATES['loved']]]]], 101 103 ]; 102 104 } 103 105 }
+90
tests/Libraries/User/CountryChangeTargetTest.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + declare(strict_types=1); 7 + 8 + namespace Tests\Libraries\User; 9 + 10 + use App\Libraries\User\CountryChangeTarget; 11 + use App\Models\Country; 12 + use App\Models\Tournament; 13 + use App\Models\User; 14 + use Carbon\CarbonImmutable; 15 + use Database\Factories\UserFactory; 16 + use Tests\TestCase; 17 + 18 + class CountryChangeTargetTest extends TestCase 19 + { 20 + public function testGetNoData(): void 21 + { 22 + $user = User::factory()->create(); 23 + 24 + $this->assertNull(CountryChangeTarget::get($user)); 25 + } 26 + 27 + public function testGetNotEnoughMonths(): void 28 + { 29 + $user = User::factory()->create(); 30 + $targetCountry = Country::factory()->create()->getKey(); 31 + UserFactory::createRecentCountryHistory($user, $targetCountry, CountryChangeTarget::minMonths() - 1); 32 + 33 + $this->assertNull(CountryChangeTarget::get($user)); 34 + } 35 + 36 + public function testGetEnoughMonths(): void 37 + { 38 + $user = User::factory()->create(); 39 + $targetCountry = Country::factory()->create()->getKey(); 40 + UserFactory::createRecentCountryHistory($user, $targetCountry, null); 41 + 42 + $this->assertSame($targetCountry, CountryChangeTarget::get($user)); 43 + } 44 + 45 + public function testGetEnoughMonthsMixed(): void 46 + { 47 + $user = User::factory()->create(); 48 + $targetCountry = Country::factory()->create()->getKey(); 49 + UserFactory::createRecentCountryHistory($user, $targetCountry, null); 50 + UserFactory::createRecentCountryHistory($user, null, CountryChangeTarget::maxMixedMonths()); 51 + 52 + $this->assertSame($targetCountry, CountryChangeTarget::get($user)); 53 + } 54 + 55 + public function testGetEnoughMonthsMixedTooMany(): void 56 + { 57 + $user = User::factory()->create(); 58 + $targetCountry = Country::factory()->create()->getKey(); 59 + UserFactory::createRecentCountryHistory($user, $targetCountry, null); 60 + UserFactory::createRecentCountryHistory($user, null, CountryChangeTarget::maxMixedMonths() + 1); 61 + 62 + $this->assertNull(CountryChangeTarget::get($user)); 63 + } 64 + 65 + public function testGetInRunningTournament(): void 66 + { 67 + $user = User::factory()->create(); 68 + $targetCountry = Country::factory()->create()->getKey(); 69 + UserFactory::createRecentCountryHistory($user, $targetCountry, null); 70 + $tournament = Tournament::factory()->create(); 71 + $tournament->registrations()->create([ 72 + 'user_id' => $user->getKey(), 73 + ]); 74 + 75 + $this->assertNull(CountryChangeTarget::get($user)); 76 + } 77 + 78 + public function testGetInPastTournament(): void 79 + { 80 + $user = User::factory()->create(); 81 + $targetCountry = Country::factory()->create()->getKey(); 82 + UserFactory::createRecentCountryHistory($user, $targetCountry, null); 83 + $tournament = Tournament::factory()->create(['end_date' => CarbonImmutable::now()->subMonths(1)]); 84 + $tournament->registrations()->create([ 85 + 'user_id' => $user->getKey(), 86 + ]); 87 + 88 + $this->assertSame($targetCountry, CountryChangeTarget::get($user)); 89 + } 90 + }
+58
tests/Libraries/User/CountryChangeTest.php
··· 1 + <?php 2 + 3 + // Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4 + // See the LICENCE file in the repository root for full licence text. 5 + 6 + declare(strict_types=1); 7 + 8 + namespace Tests\Libraries\User; 9 + 10 + use App\Exceptions\InvariantException; 11 + use App\Libraries\User\CountryChange; 12 + use App\Models\Beatmap; 13 + use App\Models\Country; 14 + use App\Models\Score\Best\Model as ScoreBestModel; 15 + use App\Models\User; 16 + use Tests\TestCase; 17 + 18 + class CountryChangeTest extends TestCase 19 + { 20 + public function testDo(): void 21 + { 22 + $user = User::factory(); 23 + foreach (Beatmap::MODES as $ruleset => $_rulesetId) { 24 + $user = $user->withPlays(rand(1, 20), $ruleset); 25 + } 26 + $user = $user->create(); 27 + foreach (Beatmap::MODES as $ruleset => $_rulesetId) { 28 + ScoreBestModel 29 + ::getClass($ruleset) 30 + ::factory(['user_id' => $user, 'country_acronym' => $user->country_acronym]) 31 + ->count(rand(1, 5)) 32 + ->create(); 33 + } 34 + $targetCountry = Country::factory()->create()->getKey(); 35 + 36 + $this->expectCountChange(fn () => $user->accountHistories()->count(), 1); 37 + CountryChange::handle($user, $targetCountry, 'test'); 38 + 39 + $user->refresh(); 40 + $this->assertSame($user->country_acronym, $targetCountry); 41 + foreach (Beatmap::MODES as $ruleset => $_rulesetId) { 42 + $this->assertSame($user->statistics($ruleset)->country_acronym, $targetCountry); 43 + 44 + foreach ($user->scoresBest($ruleset) as $score) { 45 + $this->assertSame($score->country_acronym, $targetCountry); 46 + } 47 + } 48 + } 49 + 50 + public function testDoInvalidCountry(): void 51 + { 52 + $user = User::factory()->create(); 53 + $oldCountry = $user->country_acronym; 54 + 55 + $this->expectException(InvariantException::class); 56 + CountryChange::handle($user, '__', 'test'); 57 + } 58 + }
+12
tests/Models/BeatmapsetTest.php
··· 60 60 $this->assertTrue($beatmapset->fresh()->isPending()); 61 61 } 62 62 63 + public function testNominateNATAnyRuleset(): void 64 + { 65 + $beatmapset = $this->createBeatmapset(); 66 + $user = User::factory()->withGroup('nat', [])->create(); 67 + 68 + $this->expectCountChange(fn () => $beatmapset->nominations, 1); 69 + $this->expectCountChange(fn () => $beatmapset->beatmapsetNominations()->current()->count(), 1); 70 + 71 + $beatmapset->nominate($user, $beatmapset->playmodesStr()); 72 + $beatmapset->refresh(); 73 + } 74 + 63 75 public function testQualify() 64 76 { 65 77 $beatmapset = $this->createBeatmapset();
+21
tests/Models/CommentTest.php
··· 69 69 $this->assertArrayHasKey('parent_id', $comment->validationErrors()->all()); 70 70 } 71 71 72 + /** 73 + * @dataProvider dataProviderForSetCommentableInvalid 74 + */ 75 + public function testSetCommentableInvalid($type, $id) 76 + { 77 + $comment = new Comment(['commentable_type' => $type, 'commentable_id' => $id]); 78 + $comment->setCommentable(); 79 + 80 + $this->assertNull($comment->commentable); 81 + } 82 + 72 83 public function testUnpinOnDelete() 73 84 { 74 85 $comment = Comment::factory(['pinned' => true])->create(); ··· 83 94 [null, true], 84 95 [false, false], 85 96 [true, true], 97 + ]; 98 + } 99 + 100 + public function dataProviderForSetCommentableInvalid() 101 + { 102 + return [ 103 + [null, null], 104 + [null, 10], 105 + ['beatmapset', null], 106 + ['beatmapset', 0], 86 107 ]; 87 108 } 88 109 }
+11
tests/Models/ModelCompositePrimaryKeysTest.php
··· 17 17 use App\Models\LegacyMatch; 18 18 use App\Models\UserAchievement; 19 19 use App\Models\UserClient; 20 + use App\Models\UserCountryHistory; 20 21 use App\Models\UserDonation; 21 22 use App\Models\UserGroup; 22 23 use App\Models\UserRelation; ··· 211 212 ], 212 213 [], 213 214 ['user_id', [0, 1], 2], 215 + ], 216 + [ 217 + UserCountryHistory::class, 218 + [ 219 + 'user_id' => 0, 220 + 'year_month' => '2301', 221 + 'country_acronym' => 'JP', 222 + ], 223 + ['user_id' => 1], 224 + ['count', [1, 2], 3], 214 225 ], 215 226 [ 216 227 UserDonation::class,
+79
tests/Models/ModelTest.php
··· 8 8 namespace Tests\Models; 9 9 10 10 use App\Models\Artist; 11 + use App\Models\Country; 11 12 use Exception; 12 13 use Tests\TestCase; 13 14 14 15 class ModelTest extends TestCase 15 16 { 17 + /** 18 + * @dataProvider dataProviderForDecrementInstance 19 + */ 20 + public function testDecrementInstance(callable $countryFn, bool $isChanged): void 21 + { 22 + $country = $countryFn(); 23 + $anotherCountry = Country::factory()->create(); 24 + $column = 'playcount'; 25 + 26 + $this->expectCountChange(fn () => $country->$column, $isChanged ? -1 : 0); 27 + $this->expectCountChange(fn () => $anotherCountry->$column, 0); 28 + 29 + $country->decrementInstance($column); 30 + $country->refresh(); 31 + $anotherCountry->refresh(); 32 + } 33 + 34 + /** 35 + * @dataProvider dataProviderForDecrementInstance 36 + */ 37 + public function testDecrementInstanceSpecifyCount(callable $countryFn, bool $isChanged): void 38 + { 39 + $country = $countryFn(); 40 + $anotherCountry = Country::factory()->create(); 41 + $column = 'playcount'; 42 + $change = 10; 43 + 44 + $this->expectCountChange(fn () => $country->$column, $isChanged ? -$change : 0); 45 + $this->expectCountChange(fn () => $anotherCountry->$column, 0); 46 + 47 + $country->decrementInstance($column, $change); 48 + $country->refresh(); 49 + $anotherCountry->refresh(); 50 + } 51 + 16 52 public function testGetWithHasMore() 17 53 { 18 54 Artist::factory()->count(5)->create(); ··· 57 93 $this->expectException(Exception::class); 58 94 59 95 Artist::select()->getWithHasMore(); 96 + } 97 + 98 + /** 99 + * @dataProvider dataProviderForDecrementInstance 100 + */ 101 + public function testIncrementInstance(callable $countryFn, bool $isChanged): void 102 + { 103 + $country = $countryFn(); 104 + $anotherCountry = Country::factory()->create(); 105 + $column = 'playcount'; 106 + 107 + $this->expectCountChange(fn () => $country->playcount, $isChanged ? 1 : 0); 108 + $this->expectCountChange(fn () => $anotherCountry->$column, 0); 109 + 110 + $country->incrementInstance($column); 111 + $country->refresh(); 112 + $anotherCountry->refresh(); 113 + } 114 + 115 + /** 116 + * @dataProvider dataProviderForDecrementInstance 117 + */ 118 + public function testIncrementInstanceSpecifyCount(callable $countryFn, bool $isChanged): void 119 + { 120 + $country = $countryFn(); 121 + $anotherCountry = Country::factory()->create(); 122 + $column = 'playcount'; 123 + $change = 10; 124 + 125 + $this->expectCountChange(fn () => $country->$column, $isChanged ? $change : 0); 126 + $this->expectCountChange(fn () => $anotherCountry->$column, 0); 127 + 128 + $country->incrementInstance($column, $change); 129 + $country->refresh(); 130 + $anotherCountry->refresh(); 131 + } 132 + 133 + public function dataProviderForDecrementInstance(): array 134 + { 135 + return [ 136 + [fn () => Country::factory()->create(), true], 137 + [fn () => new Country(['playcount' => 0]), false], 138 + ]; 60 139 } 61 140 }
+3 -3
tests/Models/UserNotificationTest.php
··· 32 32 33 33 $initialUserNotificationCount = UserNotification::count(); 34 34 35 - UserNotification::batchDestroy($user, BatchIdentities::fromParams([ 35 + UserNotification::batchDestroy($user->getKey(), BatchIdentities::fromParams([ 36 36 'notifications' => [ 37 37 ['id' => $notificationA->getKey()], 38 38 ], ··· 80 80 81 81 $initialUserNotificationCount = UserNotification::count(); 82 82 83 - UserNotification::batchDestroy($user, BatchIdentities::fromParams([ 83 + UserNotification::batchDestroy($user->getKey(), BatchIdentities::fromParams([ 84 84 'identities' => [ 85 85 [ 86 86 'category' => $notificationA->category, ··· 130 130 131 131 $initialUserNotificationCount = UserNotification::count(); 132 132 133 - UserNotification::batchDestroy($user, BatchIdentities::fromParams([ 133 + UserNotification::batchDestroy($user->getKey(), BatchIdentities::fromParams([ 134 134 'identities' => [ 135 135 ['object_type' => $notificationA->notifiable_type], 136 136 ],
+6 -6
yarn.lock
··· 1710 1710 lodash.uniq "^4.5.0" 1711 1711 1712 1712 caniuse-lite@^1.0.0, caniuse-lite@^1.0.30001109, caniuse-lite@^1.0.30001286: 1713 - version "1.0.30001302" 1714 - resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001302.tgz#da57ce61c51177ef3661eeed7faef392d3790aaa" 1715 - integrity sha512-YYTMO+tfwvgUN+1ZnRViE53Ma1S/oETg+J2lISsqi/ZTNThj3ZYBOKP2rHwJc37oCsPqAzJ3w2puZHn0xlLPPw== 1713 + version "1.0.30001516" 1714 + resolved "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001516.tgz" 1715 + integrity sha512-Wmec9pCBY8CWbmI4HsjBeQLqDTqV91nFVR83DnZpYyRnPI1wePDsTg0bGLPC5VU/3OIZV1fmxEea1b+tFKe86g== 1716 1716 1717 1717 caseless@~0.12.0: 1718 1718 version "0.12.0" ··· 9018 9018 string-width "^1.0.2 || 2" 9019 9019 9020 9020 word-wrap@^1.2.3: 9021 - version "1.2.3" 9022 - resolved "https://registry.yarnpkg.com/word-wrap/-/word-wrap-1.2.3.tgz#610636f6b1f703891bd34771ccb17fb93b47079c" 9023 - integrity sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ== 9021 + version "1.2.4" 9022 + resolved "https://registry.yarnpkg.com/word-wrap/-/word-wrap-1.2.4.tgz#cb4b50ec9aca570abd1f52f33cd45b6c61739a9f" 9023 + integrity sha512-2V81OA4ugVo5pRo46hAoD2ivUJx8jXmWXfUkY4KFNw0hEptvN0QfH3K4nHiwzGeKl5rFKedV48QVoqYavy4YpA== 9024 9024 9025 9025 worker-farm@^1.7.0: 9026 9026 version "1.7.0"