Tłumaczenie wszystkich user-facing stringów PL→EN (bug-report 2026-05-31 "dalej wszystko po polsku"). Alerty, przyciski, placeholdery, labelki w 12 ekranach/komponentach: BugReportFAB, AppLock(Screen/Settings/PinEntry), applock biometric prompts, doodstream error msgs, MovieDetail, PlaybackQuality, Player, SceneDetail, ScenesFilter, SiteScenes. Komentarze w kodzie zostają PL. Zmiany były WIP drugiego okna (uncommitted); wjechały do bundla 0.2.1 przy buildzie (były w working tree) — apka zainstalowana już ma EN. Ten commit utrwala je w gicie żeby nie zginęły. Czysto stringi, zero zmian logiki. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
74 lines
2.3 KiB
TypeScript
74 lines
2.3 KiB
TypeScript
import * as SecureStore from 'expo-secure-store';
|
|
import * as LocalAuthentication from 'expo-local-authentication';
|
|
|
|
const PIN_KEY = 'goon.applock.pin';
|
|
const ENABLED_KEY = 'goon.applock.enabled';
|
|
const BIO_KEY = 'goon.applock.bio_enabled';
|
|
const TIMEOUT_KEY = 'goon.applock.timeout_seconds';
|
|
|
|
export const DEFAULT_TIMEOUT_SECONDS = 60;
|
|
|
|
export interface AppLockSettings {
|
|
enabled: boolean;
|
|
bioEnabled: boolean;
|
|
timeoutSeconds: number;
|
|
hasPin: boolean;
|
|
}
|
|
|
|
export async function getSettings(): Promise<AppLockSettings> {
|
|
const [enabled, bio, timeout, pin] = await Promise.all([
|
|
SecureStore.getItemAsync(ENABLED_KEY),
|
|
SecureStore.getItemAsync(BIO_KEY),
|
|
SecureStore.getItemAsync(TIMEOUT_KEY),
|
|
SecureStore.getItemAsync(PIN_KEY),
|
|
]);
|
|
const t = timeout ? parseInt(timeout, 10) : DEFAULT_TIMEOUT_SECONDS;
|
|
return {
|
|
enabled: enabled === '1',
|
|
bioEnabled: bio === '1',
|
|
timeoutSeconds: Number.isFinite(t) ? t : DEFAULT_TIMEOUT_SECONDS,
|
|
hasPin: !!pin,
|
|
};
|
|
}
|
|
|
|
export async function setEnabled(v: boolean): Promise<void> {
|
|
await SecureStore.setItemAsync(ENABLED_KEY, v ? '1' : '0');
|
|
}
|
|
|
|
export async function setBioEnabled(v: boolean): Promise<void> {
|
|
await SecureStore.setItemAsync(BIO_KEY, v ? '1' : '0');
|
|
}
|
|
|
|
export async function setTimeoutSeconds(s: number): Promise<void> {
|
|
await SecureStore.setItemAsync(TIMEOUT_KEY, String(Math.max(0, Math.floor(s))));
|
|
}
|
|
|
|
export async function setPin(pin: string): Promise<void> {
|
|
if (!/^\d{4,8}$/.test(pin)) throw new Error('PIN must be 4-8 digits');
|
|
await SecureStore.setItemAsync(PIN_KEY, pin);
|
|
}
|
|
|
|
export async function verifyPin(pin: string): Promise<boolean> {
|
|
const stored = await SecureStore.getItemAsync(PIN_KEY);
|
|
return stored !== null && stored === pin;
|
|
}
|
|
|
|
export async function clearPin(): Promise<void> {
|
|
await SecureStore.deleteItemAsync(PIN_KEY);
|
|
}
|
|
|
|
export async function biometricAvailable(): Promise<boolean> {
|
|
const hw = await LocalAuthentication.hasHardwareAsync();
|
|
if (!hw) return false;
|
|
const enrolled = await LocalAuthentication.isEnrolledAsync();
|
|
return enrolled;
|
|
}
|
|
|
|
export async function authenticateBiometric(): Promise<boolean> {
|
|
const res = await LocalAuthentication.authenticateAsync({
|
|
promptMessage: 'Unlock Goon',
|
|
cancelLabel: 'Use PIN',
|
|
disableDeviceFallback: true,
|
|
});
|
|
return res.success;
|
|
}
|