로그아웃 SDK 대기 제거 · 온보딩 국가 시트 · 프로필 머리줄

This commit is contained in:
Sn-Kinos
2026-10-06 04:47:37 +09:00
parent 976e569a56
commit 40756d5c86
21 changed files with 277 additions and 43 deletions
+32 -3
View File
@@ -1,6 +1,7 @@
import 'dart:async';
import 'package:flutter/foundation.dart';
import 'package:flutter/services.dart';
import 'package:flutter/widgets.dart';
import 'package:shared_preferences/shared_preferences.dart';
@@ -205,14 +206,42 @@ class RemoteL10nDelegate extends LocalizationsDelegate<AppLocalizations> {
AppLocalizations.delegate.isSupported(locale);
@override
Future<AppLocalizations> load(Locale locale) => SynchronousFuture(
appL10n = RemoteAppLocalizations(lookupAppLocalizations(locale), remote),
);
Future<AppLocalizations> load(Locale locale) {
unawaited(loadCountryNames(locale));
return SynchronousFuture(
appL10n = RemoteAppLocalizations(lookupAppLocalizations(locale), remote),
);
}
@override
bool shouldReload(RemoteL10nDelegate old) => !identical(old.remote, remote);
}
/// 기기 OS 가 아는 국가 표시명(현재 앱 언어) — 코드 → 이름, **OS 정렬 순서**(Android `Collator` ·
/// iOS `localizedCompare`)대로 들어 있다. 국가 이름을 우리가 번역하지 않으려고 플랫폼 로케일 이름을 쓴다
/// (Android `Locale.getDisplayCountry` · iOS `Locale.localizedString(forRegionCode:)`).
/// 앱 언어가 바뀔 때마다 [RemoteL10nDelegate] 가 다시 읽는다. 채널이 없는 곳(위젯 테스트)은 빈 맵.
Map<String, String> platformCountryNames = const {};
const _localeChannel = MethodChannel('kr.co.fanuzu.app/locale');
Future<void> loadCountryNames(Locale locale) async {
try {
final pairs = await _localeChannel.invokeListMethod<List<Object?>>(
'countryNames',
{'locale': localeTag(locale)},
);
if (pairs == null) return;
platformCountryNames = {
for (final p in pairs)
if (p.length == 2 && p[0] is String && p[1] is String)
p[0]! as String: p[1]! as String,
};
} on Object catch (e) {
debugPrint('[Locale] country names unavailable: $e');
}
}
/// 기준 언어(ko) 문자열. `BuildContext` 가 없는 곳의 기본값으로 쓴다.
final AppLocalizations koL10n = lookupAppLocalizations(fallbackLocale);