This repository has been archived on 2026-05-26. You can view files and clone it. You cannot open issues or pull requests or push a commit.
Files
SimPas2-Windows/Form1.cs
2026-01-21 03:07:35 +09:00

2040 lines
68 KiB
C#
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
using Microsoft.Win32;
using SimPas2_Windows.Managers;
using System.Diagnostics;
using System.Globalization;
using System.Net;
using System.Xml.Linq;
using static System.Net.WebRequestMethods;
namespace SimPas2_Windows
{
public partial class SimPas2 : Form
{
private readonly PasswordManager mPassMan;
private readonly GeneratorManager mGenMan;
private readonly OtpManager mOtpMan;
private readonly PinManager mPinMan;
private readonly NoteManager mNoteMan;
private readonly QaManager mQaMan;
private readonly CreditcardManager mCcMan;
private readonly CryptoManager mCryptoMan;
private readonly CultureInfo cultureInfo;
private static readonly string mAppDataPath = Path.Combine(
Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData),
"076Soft", "SimPas");
private static readonly string mDatabasePath = Path.Combine(mAppDataPath, "SimPas.db");
private readonly byte[] mEncryptionKey;
private System.Windows.Forms.Timer otpTimer;
private string mPwKeyword;
private string mOtpKeyword;
private string mPinKeyword;
private string mNoteKeyword;
private string mQaKeyword;
private string mCcKeyword;
private string mCryptoKeyword;
private string mJpLang;
public SimPas2()
{
using (MasterPasswordForm masterForm = new MasterPasswordForm(mDatabasePath))
{
if (masterForm.ShowDialog() != DialogResult.OK)
{
Environment.Exit(0);
}
mEncryptionKey = masterForm.EncryptionKey;
}
cultureInfo = Thread.CurrentThread.CurrentUICulture;
InitializeComponent();
mPassMan = new PasswordManager(mDatabasePath, mEncryptionKey, cultureInfo.Name);
mGenMan = new GeneratorManager();
mOtpMan = new OtpManager(mDatabasePath, mEncryptionKey, cultureInfo.Name);
mPinMan = new PinManager(mDatabasePath, mEncryptionKey, cultureInfo.Name);
mNoteMan = new NoteManager(mDatabasePath, cultureInfo.Name);
mQaMan = new QaManager(mDatabasePath, mEncryptionKey, cultureInfo.Name);
mCcMan = new CreditcardManager(mDatabasePath, mEncryptionKey, cultureInfo.Name);
mCryptoMan = new CryptoManager(mDatabasePath, mEncryptionKey, cultureInfo.Name);
mPwKeyword = "";
mOtpKeyword = "";
mPinKeyword = "";
mNoteKeyword = "";
mQaKeyword = "";
mCcKeyword = "";
mCryptoKeyword = "";
mJpLang = "ja-JP";
InitializeUI();
ApplySystemTheme();
LoadPasswords(mPwKeyword);
LoadOtps(mOtpKeyword);
LoadPins(mPinKeyword);
LoadNotes(mNoteKeyword);
LoadQas(mQaKeyword);
LoadCcs(mCcKeyword);
LoadCryptos(mCryptoKeyword);
otpTimer = new System.Windows.Forms.Timer { Interval = 1000 };
otpTimer.Tick += OtpTimer_Tick;
otpTimer.Start();
}
private void InitializeUI()
{
// Window
this.FormBorderStyle = FormBorderStyle.FixedSingle;
this.MaximizeBox = false;
// Password tab tab order
pwListbox.TabIndex = 0;
pwWebsiteTextbox.TabIndex = 1;
pwUsernameTextbox.TabIndex = 2;
pwPasswordTextbox.TabIndex = 3;
pwNotesTextbox.TabIndex = 4;
pwAddButton.TabIndex = 5;
pwDeleteButton.TabIndex = 6;
pwEditButton.TabIndex = 7;
pwShowButton.TabIndex = 8;
pwDoneButton.TabIndex = 9;
pwCopyUsernameButton.TabIndex = 10;
pwCopyPasswordButton.TabIndex = 11;
// OTP tab tab order (otpAddNew)
otpWebsiteTextbox1.TabIndex = 0;
otpSecretTextbox.TabIndex = 1;
otpIssuerTextbox.TabIndex = 2;
otpAlgorithmCombobox.TabIndex = 3;
otpDigitsNumeric.TabIndex = 4;
otpDurationNumeric.TabIndex = 5;
otpAddButton.TabIndex = 6;
otpEditButton.TabIndex = 7;
otpDoneButton.TabIndex = 8;
// OTP tab tab order (otpAddOld)
otpWebsiteTextbox2.TabIndex = 0;
otpAuthTextbox.TabIndex = 1;
otpAddLegacyButton.TabIndex = 2;
// OTP tab main controls
otpDeleteButton.TabIndex = 8;
otpCopyButton.TabIndex = 9;
otpListbox.TabIndex = 10;
// PIN Codes tab tab order
pinListbox.TabIndex = 0;
pinWebsiteTextbox.TabIndex = 1;
pinCodeTextbox.TabIndex = 2;
pinNoteTextbox.TabIndex = 3;
pinAddButton.TabIndex = 4;
pinEditButton.TabIndex = 5;
pinDeleteButton.TabIndex = 6;
pinCopyButton.TabIndex = 7;
pinShowButton.TabIndex = 8;
pinDoneButton.TabIndex = 9;
// Creditcard tab tab order
ccListbox.TabIndex = 0;
ccBrandCombobox.TabIndex = 1;
ccNumberTextbox.TabIndex = 2;
ccHolderTextbox.TabIndex = 3;
ccExpirationTextbox.TabIndex = 4;
ccCvcTextbox.TabIndex = 5;
ccNotesTextbox.TabIndex = 6;
ccAddButton.TabIndex = 7;
ccEditButton.TabIndex = 8;
ccDeleteButton.TabIndex = 9;
ccShowButton.TabIndex = 10;
ccDoneButton.TabIndex = 11;
// Crypto tab tab order
cryptoListbox.TabIndex = 0;
cryptoCurrencyCombobox.TabIndex = 1;
cryptoAddressTextbox.TabIndex = 2;
cryptoSeedTextbox.TabIndex = 3;
cryptoViewkeyTextbox.TabIndex = 4;
cryptoSpendkeyTextbox.TabIndex = 5;
cryptoHeightTextbox.TabIndex = 6;
cryptoPasswordTextbox.TabIndex = 7;
cryptoNotesTextbox.TabIndex = 8;
cryptoAddButton.TabIndex = 9;
cryptoEditButton.TabIndex = 10;
cryptoDeleteButton.TabIndex = 11;
cryptoShowButton.TabIndex = 12;
cryptoDoneButton.TabIndex = 13;
// Set initial button states
genCopyButton.Enabled = false;
pwAddButton.Enabled = true;
pwEditButton.Enabled = false;
pwDeleteButton.Enabled = false;
pwCopyUsernameButton.Enabled = false;
pwCopyPasswordButton.Enabled = false;
pwShowButton.Enabled = false;
pwDoneButton.Enabled = false;
otpAddButton.Enabled = true;
otpAddLegacyButton.Enabled = true;
otpEditButton.Enabled = false;
otpDeleteButton.Enabled = false;
otpCopyButton.Enabled = false;
otpDoneButton.Enabled = false;
pinAddButton.Enabled = true;
pinEditButton.Enabled = false;
pinDeleteButton.Enabled = false;
pinCopyButton.Enabled = false;
pinShowButton.Enabled = false;
pinDoneButton.Enabled = false;
noteAddEditButton.Enabled = true;
noteAddEditButton.Text = cultureInfo.Name == mJpLang ? "追加" : "Add";
noteTextbox.Enabled = false;
noteDeleteButton.Enabled = false;
noteSaveButton.Enabled = false;
noteDoneButton.Enabled = false;
qaAddButton.Enabled = true;
qaDeleteButton.Enabled = false;
qaEditButton.Enabled = false;
qaCopyButton.Enabled = false;
qaShowButton.Enabled = false;
qaDoneButton.Enabled = false;
ccAddButton.Enabled = true;
ccDeleteButton.Enabled = false;
ccEditButton.Enabled = false;
ccShowButton.Enabled = false;
ccDoneButton.Enabled = false;
cryptoAddButton.Enabled = true;
cryptoDeleteButton.Enabled = false;
cryptoEditButton.Enabled = false;
cryptoShowButton.Enabled = false;
cryptoDoneButton.Enabled = false;
// Initialize ComboBox and NumericUpDown
otpAlgorithmCombobox.SelectedIndex = 0; // SHA1
otpDigitsNumeric.Value = 6;
otpDurationNumeric.Value = 30;
}
private void ApplySystemTheme()
{
bool isDarkMode = Registry.GetValue(
@"HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Themes\Personalize",
"AppsUseLightTheme", 1)?.ToString() == "0";
Color backColor = isDarkMode ? Color.FromArgb(0x12, 0x0f, 0x12) : Color.FromArgb(0xfc, 0xfc, 0xfc);
Color disableColor = isDarkMode ? Color.FromArgb(0xbd, 0xb4, 0xbd) : Color.FromArgb(0x74, 0x6c, 0x75);
Color foreColor = isDarkMode ? Color.FromArgb(0xfc, 0xfc, 0xfc) : Color.FromArgb(0x23, 0x20, 0x23);
Color tabBackColor = isDarkMode ? Color.FromArgb(0x23, 0x20, 0x23) : Color.FromArgb(0xf6, 0xf6, 0xf6);
Color tabForeColor = isDarkMode ? Color.FromArgb(0xf6, 0xf6, 0xf6) : Color.FromArgb(0x23, 0x20, 0x23);
Color elementBackColor = isDarkMode ? Color.FromArgb(0x44, 0x3b, 0x44) : Color.FromArgb(0xcf, 0xcb, 0xcf);
Color elementForeColor = isDarkMode ? Color.FromArgb(0xcf, 0xcb, 0xcf) : Color.FromArgb(0x44, 0x3b, 0x44);
this.BackColor = backColor;
this.ForeColor = foreColor;
foreach (Control control in this.Controls)
{
control.BackColor = elementBackColor;
control.ForeColor = elementForeColor;
if (control is TabControl tabControl)
{
tabControl.DrawMode = TabDrawMode.OwnerDrawFixed;
tabControl.DrawItem += (sender, e) =>
{
var tab = tabControl.TabPages[e.Index];
var g = e.Graphics;
using (SolidBrush brush = new SolidBrush(tabBackColor))
{
g.FillRectangle(brush, e.Bounds);
}
using (SolidBrush brush = new SolidBrush(tabForeColor))
{
g.DrawString(tab.Text, tabControl.Font, brush, e.Bounds.Left + 5, e.Bounds.Top + 5);
}
if (e.State == DrawItemState.Selected)
{
using (Pen pen = new Pen(tabForeColor))
{
g.DrawRectangle(pen, e.Bounds.X + 2, e.Bounds.Y + 2, e.Bounds.Width - 4, e.Bounds.Height - 4);
}
}
};
foreach (TabPage tabPage in tabControl.TabPages)
{
tabPage.BackColor = backColor;
tabPage.ForeColor = foreColor;
ApplyThemeToControls(tabPage.Controls, tabBackColor, disableColor, tabForeColor);
}
}
}
}
private void ApplyThemeToControls(Control.ControlCollection controls, Color backColor, Color disableColor, Color foreColor)
{
foreach (Control control in controls)
{
if (!(control is Label))
{
control.BackColor = backColor;
}
control.ForeColor = foreColor;
if (control is Button button)
{
button.FlatStyle = FlatStyle.Flat;
button.FlatAppearance.BorderSize = 1;
button.Paint += (sender, e) =>
{
Button btn = (Button)sender;
e.Graphics.Clear(btn.BackColor);
TextFormatFlags flags = TextFormatFlags.HorizontalCenter | TextFormatFlags.VerticalCenter;
Color textColor = btn.Enabled ? foreColor : disableColor;
TextRenderer.DrawText(e.Graphics, btn.Text, btn.Font, btn.ClientRectangle, textColor, flags);
};
}
if (control.HasChildren)
{
ApplyThemeToControls(control.Controls, backColor, disableColor, foreColor);
}
}
}
private void genGenerateButton_Click(object sender, EventArgs e)
{
genPasswordTextbox.Text = mGenMan.GeneratePassword(genSecureCheckbox.Checked, (int)genNumeric.Value);
genCopyButton.Enabled = true;
}
private async void genCopyButton_Click(object sender, EventArgs e)
{
if (!string.IsNullOrEmpty(genPasswordTextbox.Text))
{
try
{
Clipboard.SetText(genPasswordTextbox.Text);
await Task.Delay(45000); // 45秒
if (Clipboard.GetText() == genPasswordTextbox.Text)
{
Clipboard.Clear();
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"パスワードのコピーに失敗:{ex.Message}"
: $"Failed to copy password: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
string mes = cultureInfo.Name == mJpLang
? "コピー出来るパスワードではありません。"
: "No password to copy.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void pwListbox_SelectedIndexChanged(object sender, EventArgs e)
{
if (pwListbox.SelectedItem is Item selected)
{
var passwords = mPassMan.GetAll();
var password = passwords.FirstOrDefault(p => p.Id == selected.Id);
if (password != default)
{
pwWebsiteTextbox.Text = password.Website;
pwUsernameTextbox.Text = password.Username;
pwPasswordTextbox.Text = password.Password;
pwNotesTextbox.Text = password.Note;
pwAddButton.Enabled = false;
pwEditButton.Enabled = true;
pwDeleteButton.Enabled = true;
pwCopyUsernameButton.Enabled = true;
pwCopyPasswordButton.Enabled = true;
pwShowButton.Enabled = true;
pwDoneButton.Enabled = true;
}
else
{
ClearPasswordFields();
}
}
}
private void pwAddButton_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(pwWebsiteTextbox.Text) ||
string.IsNullOrWhiteSpace(pwUsernameTextbox.Text) ||
string.IsNullOrWhiteSpace(pwPasswordTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "ウェブサイト、ユーザー名及び、パスワードを御入力下さい。"
: "Please fill in the website, user/email, and password.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
mPassMan.AddPassword(pwWebsiteTextbox.Text, pwUsernameTextbox.Text, pwPasswordTextbox.Text, pwNotesTextbox.Text);
LoadPasswords(mPwKeyword);
ClearPasswordFields();
Debug.WriteLine(cultureInfo.Name);
string mes = cultureInfo.Name == mJpLang
? "パスワードを追加しました。"
: "Password added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"パスワードの追加に失敗:{ex.Message}"
: $"Failed to add password: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void pwDeleteButton_Click(object sender, EventArgs e)
{
if (pwListbox.SelectedItem is Item selected)
{
string mes = cultureInfo.Name == mJpLang
? $"本当に {selected.DisplayText} のパスワードを削除しますか?"
: $"Are you sure you want to delete the password for {selected.DisplayText}?";
string tit = cultureInfo.Name == mJpLang
? "削除の確認"
: "Confirm Delete";
var res = MessageBox.Show(mes, tit, MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (res == DialogResult.Yes)
{
if (mPassMan.DeletePassword(selected.Id))
{
LoadPasswords(mPwKeyword);
ClearPasswordFields();
}
else
{
mes = cultureInfo.Name == mJpLang
? "パスワードの削除に失敗。"
: "Failed to delete password";
tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}
private void pwEditButton_Click(object sender, EventArgs e)
{
if (pwListbox.SelectedItem is Item selected)
{
try
{
if (mPassMan.EditPassword(selected.Id, pwWebsiteTextbox.Text, pwUsernameTextbox.Text, pwPasswordTextbox.Text, pwNotesTextbox.Text))
{
LoadPasswords(mPwKeyword);
ClearPasswordFields();
string mes = cultureInfo.Name == mJpLang
? "パスワードの変更に成功。"
: "Password changed successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
else
{
string mes = cultureInfo.Name == mJpLang
? "パスワードの変更に失敗。"
: "Failed to change password.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"パスワードの変更に失敗:{ex.Message}"
: $"Failed to change password: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private async void pwCopyUsernameButton_Click(object sender, EventArgs e)
{
if (!string.IsNullOrEmpty(pwUsernameTextbox.Text))
{
try
{
Clipboard.SetText(pwUsernameTextbox.Text);
await Task.Delay(45000); // 45秒
if (Clipboard.GetText() == pwUsernameTextbox.Text)
{
Clipboard.Clear();
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"ユーザー名のコピーに失敗:{ex.Message}"
: $"Failed to copy user/email: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
string mes = cultureInfo.Name == mJpLang
? "コピー出来るユーザー名ではありません。"
: "No user/email to copy.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private async void pwCopyPasswordButton_Click(object sender, EventArgs e)
{
if (!string.IsNullOrEmpty(pwPasswordTextbox.Text))
{
try
{
Clipboard.SetText(pwPasswordTextbox.Text);
await Task.Delay(45000); // 45秒
if (Clipboard.GetText() == pwPasswordTextbox.Text)
{
Clipboard.Clear();
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"パスワードのコピーに失敗:{ex.Message}"
: $"Failed to copy password: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
string mes = cultureInfo.Name == mJpLang
? "コピー出来るパスワードではありません。"
: "No password to copy.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void pwShowButton_Click(object sender, EventArgs e)
{
pwPasswordTextbox.UseSystemPasswordChar = !pwPasswordTextbox.UseSystemPasswordChar;
}
private void pwDoneButton_Click(object sender, EventArgs e)
{
LoadPasswords(mPwKeyword);
ClearPasswordFields();
}
private void pwSearchTextbox_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == (char)13)
{
mPwKeyword = pwSearchTextbox.Text;
LoadPasswords(pwSearchTextbox.Text);
ClearPasswordFields();
e.Handled = true;
}
}
private void otpAddLegacyButton_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(otpWebsiteTextbox2.Text) ||
string.IsNullOrWhiteSpace(otpAuthTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "ウェブサイト及びOTP Authを御入力下さい。"
: "Please fill in the website and OTP Auth.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
var (secret, issuer, algorithm, duration, digits) = mOtpMan.ParseOtpAuthUrl(otpAuthTextbox.Text);
mOtpMan.AddOtp(otpWebsiteTextbox2.Text, secret, issuer, algorithm, duration, digits, "");
LoadOtps(mOtpKeyword);
ClearOtpFields();
string mes = cultureInfo.Name == mJpLang
? "OTPの追加に成功。"
: "OTP added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"OTPの追加に失敗{ex.Message}"
: $"Failed to add OTP: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void otpAddButton_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(otpWebsiteTextbox1.Text) ||
string.IsNullOrWhiteSpace(otpSecretTextbox.Text) ||
string.IsNullOrWhiteSpace(otpIssuerTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "ウェブサイト、秘密鍵及び、発行者を御入力下さい。"
: "Please fill in the website, secret, and issuer.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
mOtpMan.AddOtp(
otpWebsiteTextbox1.Text,
otpSecretTextbox.Text,
otpIssuerTextbox.Text,
otpAlgorithmCombobox.Text,
(int)otpDurationNumeric.Value,
(int)otpDigitsNumeric.Value,
""
);
LoadOtps(mOtpKeyword);
ClearOtpFields();
string mes = cultureInfo.Name == mJpLang
? "OTPの追加に成功。"
: "OTP added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"OTPの追加に失敗{ex.Message}"
: $"Failed to add OTP: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void otpEditButton_Click(object sender, EventArgs e)
{
if (otpListbox.SelectedItem is Item selected)
{
if (string.IsNullOrWhiteSpace(otpWebsiteTextbox1.Text) ||
string.IsNullOrWhiteSpace(otpSecretTextbox.Text) ||
string.IsNullOrWhiteSpace(otpIssuerTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "ウェブサイト、秘密鍵及び、発行者を御入力下さい。"
: "Please fill in the website, secret, and issuer.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
if (mOtpMan.EditOtp(
selected.Id,
otpWebsiteTextbox1.Text,
otpSecretTextbox.Text,
otpIssuerTextbox.Text,
otpAlgorithmCombobox.Text,
(int)otpDurationNumeric.Value,
(int)otpDigitsNumeric.Value,
""
))
{
LoadOtps(mOtpKeyword);
ClearOtpFields();
string mes = cultureInfo.Name == mJpLang
? "OTPの変更に成功。"
: "OTP changed successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
else
{
string mes = cultureInfo.Name == mJpLang
? "OTPの更新に失敗。"
: "Failed to change OTP.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"OTPの更新に失敗{ex.Message}"
: $"Failed to change OTP: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void otpDeleteButton_Click(object sender, EventArgs e)
{
if (otpListbox.SelectedItem is Item selected)
{
string mes = cultureInfo.Name == mJpLang
? $"本当に {selected.DisplayText} のOTPを削除しますか"
: $"Are you sure you want to delete the OTP for {selected.DisplayText}?";
string tit = cultureInfo.Name == mJpLang
? "削除の確認"
: "Confirm Delete";
var res = MessageBox.Show(mes, tit, MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (res == DialogResult.Yes)
{
if (mOtpMan.DeleteOtp(selected.Id))
{
LoadOtps(mOtpKeyword);
ClearOtpFields();
}
else
{
mes = cultureInfo.Name == mJpLang
? "OTPの削除に失敗。"
: "Failed to delete OTP.";
tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}
private async void otpCopyButton_Click(object sender, EventArgs e)
{
if (!string.IsNullOrEmpty(otpCodeLabel.Text))
{
try
{
Clipboard.SetText(otpCodeLabel.Text);
await Task.Delay(30000); // 30秒
if (Clipboard.GetText() == otpCodeLabel.Text)
{
Clipboard.Clear();
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"OTPのコピーに失敗{ex.Message}"
: $"Failed to copy OTP: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
MessageBox.Show($"Failed to copy OTP: {ex.Message}", "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
string mes = cultureInfo.Name == mJpLang
? "コピー出来るOTPではありません。"
: "No OTP to copy.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void otpDoneButton_Click(object sender, EventArgs e)
{
LoadOtps(mOtpKeyword);
ClearOtpFields();
}
private void otpSearchTextbox_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == (char)13)
{
mOtpKeyword = otpSearchTextbox.Text;
LoadOtps(otpSearchTextbox.Text);
ClearOtpFields();
e.Handled = true;
}
}
private void otpListbox_SelectedIndexChanged(object sender, EventArgs e)
{
if (otpListbox.SelectedItem is Item selected)
{
var otps = mOtpMan.GetAll();
var otp = otps.FirstOrDefault(o => o.Id == selected.Id);
if (otp != default)
{
UpdateOtpCode(otp);
otpWebsiteTextbox1.Text = otp.Website;
otpIssuerTextbox.Text = otp.Issuer;
otpSecretTextbox.Text = otp.Secret;
otpDigitsNumeric.Value = otp.Digits;
otpDurationNumeric.Value = otp.Duration;
otpAlgorithmCombobox.SelectedItem = otp.Algorithm ?? "SHA1";
otpAddButton.Enabled = false;
otpAddLegacyButton.Enabled = false;
otpEditButton.Enabled = true;
otpDeleteButton.Enabled = true;
otpCopyButton.Enabled = true;
otpDoneButton.Enabled = true;
}
else
{
ClearOtpFields();
string mes = cultureInfo.Name == mJpLang
? "ID {selected.Id} を持つOTPをデータベースに見つけられませんでした。"
: "OTP with ID {selected.Id} not found in database.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
ClearOtpFields();
}
}
private void pinAddButton_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(pinWebsiteTextbox.Text) ||
string.IsNullOrWhiteSpace(pinCodeTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "ウェブサイト及び暗証番号を御入力下さい。"
: "Please fill in the website and pincode.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
mPinMan.AddPin(pinWebsiteTextbox.Text, pinCodeTextbox.Text, pinNoteTextbox.Text);
LoadPins(mPinKeyword);
ClearPinFields();
string mes = cultureInfo.Name == mJpLang
? "暗証番号の追加に成功。"
: "Pincode added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"暗証番号の追加に失敗:{ex.Message}"
: $"Failed to add pincode: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void pinEditButton_Click(object sender, EventArgs e)
{
if (pinListbox.SelectedItem is Item selected)
{
if (mPinMan.EditPin(selected.Id, pinWebsiteTextbox.Text, pinCodeTextbox.Text, pinNoteTextbox.Text))
{
LoadPins(mPinKeyword);
ClearPinFields();
string mes = cultureInfo.Name == mJpLang
? "暗証番号の変更に成功。"
: "Pincode changed successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
else
{
string mes = cultureInfo.Name == mJpLang
? $"暗証番号の変更に失敗。"
: $"Failed to change pincode.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void pinDeleteButton_Click(object sender, EventArgs e)
{
if (pinListbox.SelectedItem is Item selected)
{
string mes = cultureInfo.Name == mJpLang
? $"本当に {selected.DisplayText} の暗証番号を削除しますか?"
: $"Are you sure you want to delete the pincode for {selected.DisplayText}?";
string tit = cultureInfo.Name == mJpLang
? "削除の確認"
: "Confirm Delete";
var res = MessageBox.Show(mes, tit, MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (res == DialogResult.Yes)
{
if (mPinMan.DeletePin(selected.Id))
{
LoadPins(mPinKeyword);
ClearPinFields();
}
else
{
mes = cultureInfo.Name == mJpLang
? "暗証番号の削除に失敗。"
: "Failed to delete pincode";
tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}
private async void pinCopyButton_Click(object sender, EventArgs e)
{
if (!string.IsNullOrEmpty(pinCodeTextbox.Text))
{
try
{
Clipboard.SetText(pinCodeTextbox.Text);
await Task.Delay(45000); // 45秒
if (Clipboard.GetText() == pinCodeTextbox.Text)
{
Clipboard.Clear();
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"暗証番号のコピーに失敗:{ex.Message}"
: $"Failed to copy pincode: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
string mes = cultureInfo.Name == mJpLang
? "ID {selected.Id} を持つ暗証番号をデータベースに見つけられませんでした。"
: "Pincode with ID {selected.Id} not found in database.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void pinShowButton_Click(object sender, EventArgs e)
{
pinCodeTextbox.UseSystemPasswordChar = !pinCodeTextbox.UseSystemPasswordChar;
}
private void pinDoneButton_Click(object sender, EventArgs e)
{
LoadPins(mPinKeyword);
ClearPinFields();
}
private void pinListbox_SelectedIndexChanged(object sender, EventArgs e)
{
if (pinListbox.SelectedItem is Item selected)
{
var pins = mPinMan.GetAll();
var pin = pins.FirstOrDefault(o => o.Id == selected.Id);
if (pin != default)
{
pinWebsiteTextbox.Text = pin.Website;
pinCodeTextbox.Text = pin.Pincode;
pinNoteTextbox.Text = pin.Note;
pinAddButton.Enabled = false;
pinEditButton.Enabled = true;
pinDeleteButton.Enabled = true;
pinCopyButton.Enabled = true;
pinShowButton.Enabled = true;
pinDoneButton.Enabled = true;
}
else
{
ClearPinFields();
string mes = cultureInfo.Name == mJpLang
? $"ID {selected.Id} を持つ暗証番号をデータベースに見つけられませんでした。"
: $"Pincode with ID {selected.Id} not found in database.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
ClearPinFields();
}
}
private void pinSearchTextbox_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == (char)13)
{
mPinKeyword = pinSearchTextbox.Text;
LoadPins(pinSearchTextbox.Text);
ClearPinFields();
e.Handled = true;
}
}
private void noteAddEditButton_Click(object sender, EventArgs e)
{
if (noteListbox.SelectedItem is Item selected)
{
try
{
mNoteMan.EditNote(selected.Id, noteTitleTextbox.Text);
LoadNotes(mNoteKeyword);
ClearNoteFields();
string mes = cultureInfo.Name == mJpLang
? "メモの変更に成功。"
: "Note changed successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"メモの変更に失敗:{ex.Message}"
: $"Failed to change note: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
try
{
mNoteMan.AddNote(noteTitleTextbox.Text);
LoadNotes(mNoteKeyword);
ClearNoteFields();
string mes = cultureInfo.Name == mJpLang
? "メモの追加に成功。"
: "Note added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"メモの追加に失敗:{ex.Message}"
: $"Failed to add note: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void noteListbox_SelectedIndexChanged(object sender, EventArgs e)
{
if (noteListbox.SelectedItem is Item selected)
{
var notes = mNoteMan.GetAll();
var note = notes.FirstOrDefault(o => o.Id == selected.Id);
if (note != default)
{
noteTitleTextbox.Text = note.Name;
noteTextbox.Text = note.Text;
noteTextbox.Enabled = true;
noteAddEditButton.Text = cultureInfo.Name == mJpLang ? "編集" : "Edit";
noteDeleteButton.Enabled = true;
noteDoneButton.Enabled = true;
noteSaveButton.Enabled = true;
}
else
{
ClearNoteFields();
string mes = cultureInfo.Name == mJpLang
? $"ID {selected.Id} を持つメモをデータベースに見つけられませんでした。"
: $"Note with ID {selected.Id} not found in database.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
ClearNoteFields();
}
}
private void noteDeleteButton_Click(object sender, EventArgs e)
{
if (noteListbox.SelectedItem is Item selected)
{
string mes = cultureInfo.Name == mJpLang
? $"本当に {selected.DisplayText} のメモを削除しますか?"
: $"Are you sure you want to delete the note for {selected.DisplayText}?";
string tit = cultureInfo.Name == mJpLang
? "削除の確認"
: "Confirm Delete";
var res = MessageBox.Show(mes, tit, MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (res == DialogResult.Yes)
{
if (mNoteMan.DeleteNote(selected.Id))
{
LoadNotes(mNoteKeyword);
ClearNoteFields();
}
else
{
mes = cultureInfo.Name == mJpLang
? "メモの削除に失敗。"
: "Failed to delete note";
tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}
private void NoteSearchTextbox_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == (char)13)
{
mNoteKeyword = noteSearchTextbox.Text;
LoadNotes(noteSearchTextbox.Text);
ClearNoteFields();
e.Handled = true;
}
}
private void noteSaveButton_Click(object sender, EventArgs e)
{
if (noteListbox.SelectedItem is Item selected)
{
try
{
mNoteMan.SaveNote(selected.Id, noteTextbox.Text);
LoadNotes(mNoteKeyword);
string mes = cultureInfo.Name == mJpLang
? "メモの保存に成功。"
: "Note saved successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"メモの保存に失敗:{ex.Message}"
: $"Failed to save note: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void noteDoneButton_Click(object sender, EventArgs e)
{
LoadNotes(mNoteKeyword);
ClearNoteFields();
}
private void qaAddButton_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(qaWebsiteTextbox.Text) ||
string.IsNullOrWhiteSpace(qaQuestionTextbox.Text) ||
string.IsNullOrWhiteSpace(qaAnswerTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "ウェブサイト、質問及び、回答を御入力下さい。"
: "Please fill in the website, question, and answer.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
mQaMan.AddQa(qaWebsiteTextbox.Text, qaQuestionTextbox.Text, qaAnswerTextbox.Text, qaNoteTextbox.Text);
LoadQas(mQaKeyword);
ClearQaFields();
string mes = cultureInfo.Name == mJpLang
? "秘密質問を追加しました。"
: "Secret question added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"秘密質問の追加に失敗:{ex.Message}"
: $"Failed to add secret question: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void qaDeleteButton_Click(object sender, EventArgs e)
{
if (qaListbox.SelectedItem is Item selected)
{
string mes = cultureInfo.Name == mJpLang
? $"本当に {selected.DisplayText} の秘密質問を削除しますか?"
: $"Are you sure you want to delete the secret question for {selected.DisplayText}?";
string tit = cultureInfo.Name == mJpLang
? "削除の確認"
: "Confirm Delete";
var res = MessageBox.Show(mes, tit, MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (res == DialogResult.Yes)
{
if (mQaMan.DeleteQa(selected.Id))
{
LoadQas(mQaKeyword);
ClearQaFields();
}
else
{
mes = cultureInfo.Name == mJpLang
? "秘密質問の削除に失敗。"
: "Failed to delete secret question";
tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}
private void qaEditButton_Click(object sender, EventArgs e)
{
if (qaListbox.SelectedItem is Item selected)
{
if (mQaMan.EditQa(selected.Id, qaWebsiteTextbox.Text, qaQuestionTextbox.Text, qaAnswerTextbox.Text, qaNoteTextbox.Text))
{
LoadQas(mQaKeyword);
ClearQaFields();
string mes = cultureInfo.Name == mJpLang
? "秘密質問の変更に成功。"
: "Secret question changed successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
else
{
string mes = cultureInfo.Name == mJpLang
? "秘密質問の変更に失敗。"
: "Failed to change secret question.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private async void qaCopyButton_Click(object sender, EventArgs e)
{
if (!string.IsNullOrEmpty(qaAnswerTextbox.Text))
{
try
{
Clipboard.SetText(qaAnswerTextbox.Text);
await Task.Delay(45000); // 45秒
if (Clipboard.GetText() == qaAnswerTextbox.Text)
{
Clipboard.Clear();
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"秘密質問のコピーに失敗:{ex.Message}"
: $"Failed to copy secret question: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
else
{
string mes = cultureInfo.Name == mJpLang
? "コピー出来る秘密質問ではありません。"
: "No secret question to copy.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void qaShowButton_Click(object sender, EventArgs e)
{
qaAnswerTextbox.UseSystemPasswordChar = !qaAnswerTextbox.UseSystemPasswordChar;
}
private void qaDoneButton_Click(object sender, EventArgs e)
{
LoadQas(mQaKeyword);
ClearQaFields();
}
private void qaListbox_SelectedIndexChanged(object sender, EventArgs e)
{
if (qaListbox.SelectedItem is Item selected)
{
var qas = mQaMan.GetAll();
var qa = qas.FirstOrDefault(p => p.Id == selected.Id);
if (qa != default)
{
qaWebsiteTextbox.Text = qa.Website;
qaQuestionTextbox.Text = qa.Question;
qaAnswerTextbox.Text = qa.Answer;
qaNoteTextbox.Text = qa.Note;
qaAddButton.Enabled = false;
qaEditButton.Enabled = true;
qaDeleteButton.Enabled = true;
qaCopyButton.Enabled = true;
qaShowButton.Enabled = true;
qaDoneButton.Enabled = true;
}
else
{
ClearQaFields();
}
}
}
private void qaSearchTextbox_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == (char)13)
{
mQaKeyword = qaSearchTextbox.Text;
LoadNotes(qaSearchTextbox.Text);
ClearQaFields();
e.Handled = true;
}
}
private void ccListbox_SelectedIndexChanged(object sender, EventArgs e)
{
if (ccListbox.SelectedItem is Item selected)
{
var ccs = mCcMan.GetAll();
var cc = ccs.FirstOrDefault(p => p.Id == selected.Id);
if (cc != default)
{
ccBrandCombobox.SelectedItem = cc.Brand ?? "Mastercard";
ccNumberTextbox.Text = cc.Cardnumber;
ccHolderTextbox.Text = cc.Holdername;
ccExpirationTextbox.Text = cc.Expiration;
ccCvcTextbox.Text = cc.Cvc;
ccNotesTextbox.Text = cc.Note;
ccAddButton.Enabled = false;
ccEditButton.Enabled = true;
ccDeleteButton.Enabled = true;
ccShowButton.Enabled = true;
ccDoneButton.Enabled = true;
}
else
{
ClearCcFields();
}
}
}
private void ccSearchTextbox_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == (char)13)
{
mCcKeyword = ccSearchTextbox.Text;
LoadCcs(ccSearchTextbox.Text);
ClearCcFields();
e.Handled = true;
}
}
private void ccAddButton_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(ccBrandCombobox.Text) ||
string.IsNullOrWhiteSpace(ccNumberTextbox.Text) ||
string.IsNullOrWhiteSpace(ccExpirationTextbox.Text) ||
string.IsNullOrWhiteSpace(ccCvcTextbox.Text) ||
string.IsNullOrWhiteSpace(ccHolderTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "ブランド、カード番号、氏名、有効期限及び、CVCを御入力下さい。"
: "Please fill in the brand, card number, full name, expiration, and CVC.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
mCcMan.AddCc(ccBrandCombobox.Text, ccNumberTextbox.Text, ccExpirationTextbox.Text, ccCvcTextbox.Text, ccHolderTextbox.Text, ccNotesTextbox.Text);
LoadCcs(mCcKeyword);
ClearCcFields();
string mes = cultureInfo.Name == mJpLang
? "クレジットカードを追加しました。"
: "Creditcard added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"クレジットカードの追加に失敗:{ex.Message}"
: $"Failed to add creditcard: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void ccDeleteButton_Click(object sender, EventArgs e)
{
if (ccListbox.SelectedItem is Item selected)
{
string mes = cultureInfo.Name == mJpLang
? $"本当に {selected.DisplayText} のクレジットカードを削除しますか?"
: $"Are you sure you want to delete the creditcard for {selected.DisplayText}?";
string tit = cultureInfo.Name == mJpLang
? "削除の確認"
: "Confirm Delete";
var res = MessageBox.Show(mes, tit, MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (res == DialogResult.Yes)
{
if (mCcMan.DeleteCc(selected.Id))
{
LoadCcs(mCcKeyword);
ClearCcFields();
}
else
{
mes = cultureInfo.Name == mJpLang
? "クレジットカードの削除に失敗。"
: "Failed to delete creditcard";
tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}
private void ccEditButton_Click(object sender, EventArgs e)
{
if (ccListbox.SelectedItem is Item selected)
{
if (mCcMan.EditCc(selected.Id, ccBrandCombobox.Text, ccNumberTextbox.Text, ccExpirationTextbox.Text, ccCvcTextbox.Text, ccHolderTextbox.Text, ccNotesTextbox.Text))
{
LoadCcs(mCcKeyword);
ClearCcFields();
string mes = cultureInfo.Name == mJpLang
? "クレジットカードの変更に成功。"
: "Creditcard changed successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
else
{
string mes = cultureInfo.Name == mJpLang
? "クレジットカードの変更に失敗。"
: "Failed to change creditcard.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void ccShowButton_Click(object sender, EventArgs e)
{
ccNumberTextbox.UseSystemPasswordChar = !ccNumberTextbox.UseSystemPasswordChar;
ccCvcTextbox.UseSystemPasswordChar = !ccCvcTextbox.UseSystemPasswordChar;
}
private void ccDoneButton_Click(object sender, EventArgs e)
{
LoadCcs(mCcKeyword);
ClearCcFields();
}
private void cryptoListbox_SelectedIndexChanged(object sender, EventArgs e)
{
if (cryptoListbox.SelectedItem is Item selected)
{
var cryptos = mCryptoMan.GetAll();
var crypto = cryptos.FirstOrDefault(p => p.Id == selected.Id);
if (crypto != default)
{
cryptoCurrencyCombobox.SelectedItem = crypto.Currency ?? "XMR";
cryptoNameTextbox.Text = crypto.Name;
cryptoAddressTextbox.Text = crypto.Address;
cryptoSeedTextbox.Text = crypto.Seed;
cryptoViewkeyTextbox.Text = crypto.Viewkey;
cryptoSpendkeyTextbox.Text = crypto.Spendkey;
cryptoHeightTextbox.Text = crypto.Height;
cryptoPasswordTextbox.Text = crypto.Password;
cryptoNotesTextbox.Text = crypto.Note;
cryptoAddButton.Enabled = false;
cryptoEditButton.Enabled = true;
cryptoDeleteButton.Enabled = true;
cryptoShowButton.Enabled = true;
cryptoDoneButton.Enabled = true;
}
else
{
ClearCryptoFields();
}
}
}
private void cryptoSearchTextbox_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == (char)13)
{
mCryptoKeyword = cryptoSearchTextbox.Text;
LoadCryptos(cryptoSearchTextbox.Text);
ClearCryptoFields();
e.Handled = true;
}
}
private void cryptoAddButton_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(cryptoCurrencyCombobox.Text) ||
string.IsNullOrWhiteSpace(cryptoNameTextbox.Text) ||
string.IsNullOrWhiteSpace(cryptoAddressTextbox.Text))
{
string mes = cultureInfo.Name == mJpLang
? "通貨、ウォレット名及び、住所を御入力下さい。"
: "Please fill in the currency, wallet name, and address.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
try
{
mCryptoMan.AddCrypto(cryptoCurrencyCombobox.Text, cryptoNameTextbox.Text, cryptoAddressTextbox.Text, cryptoSeedTextbox.Text, cryptoViewkeyTextbox.Text, cryptoSpendkeyTextbox.Text, cryptoHeightTextbox.Text, cryptoPasswordTextbox.Text, cryptoNotesTextbox.Text);
LoadCryptos(mCryptoKeyword);
ClearCryptoFields();
string mes = cultureInfo.Name == mJpLang
? "仮想通貨を追加しました。"
: "Cryptocurrency added successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"仮想通貨の追加に失敗:{ex.Message}"
: $"Failed to add cryptocurrency: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void cryptoDeleteButton_Click(object sender, EventArgs e)
{
if (cryptoListbox.SelectedItem is Item selected)
{
string mes = cultureInfo.Name == mJpLang
? $"本当に {selected.DisplayText} の仮想通貨を削除しますか?"
: $"Are you sure you want to delete the cryptocurrency for {selected.DisplayText}?";
string tit = cultureInfo.Name == mJpLang
? "削除の確認"
: "Confirm Delete";
var res = MessageBox.Show(mes, tit, MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (res == DialogResult.Yes)
{
if (mCryptoMan.DeleteCrypto(selected.Id))
{
LoadCryptos(mCryptoKeyword);
ClearCryptoFields();
}
else
{
mes = cultureInfo.Name == mJpLang
? "暗号通貨の削除に失敗。"
: "Failed to delete cryptocurrency";
tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}
private void cryptoEditButton_Click(object sender, EventArgs e)
{
if (cryptoListbox.SelectedItem is Item selected)
{
if (mCryptoMan.EditCrypto(selected.Id, cryptoCurrencyCombobox.Text, cryptoNameTextbox.Text, cryptoAddressTextbox.Text, cryptoSeedTextbox.Text, cryptoViewkeyTextbox.Text, cryptoSpendkeyTextbox.Text, cryptoHeightTextbox.Text, cryptoPasswordTextbox.Text, cryptoNotesTextbox.Text))
{
LoadCryptos(mCryptoKeyword);
ClearCryptoFields();
string mes = cultureInfo.Name == mJpLang
? "暗号通貨の変更に成功。"
: "Cryptocurrency changed successfully.";
string tit = cultureInfo.Name == mJpLang
? "成功"
: "Success";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Information);
}
else
{
string mes = cultureInfo.Name == mJpLang
? "暗号通貨の変更に失敗。"
: "Failed to change cryptocurrency.";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void cryptoShowButton_Click(object sender, EventArgs e)
{
cryptoSeedTextbox.UseSystemPasswordChar = !cryptoSeedTextbox.UseSystemPasswordChar;
cryptoViewkeyTextbox.UseSystemPasswordChar = !cryptoViewkeyTextbox.UseSystemPasswordChar;
cryptoSpendkeyTextbox.UseSystemPasswordChar = !cryptoSpendkeyTextbox.UseSystemPasswordChar;
cryptoHeightTextbox.UseSystemPasswordChar = !cryptoHeightTextbox.UseSystemPasswordChar;
}
private void cryptoDoneButton_Click(object sender, EventArgs e)
{
LoadCryptos(mCryptoKeyword);
ClearCryptoFields();
}
private void OtpTimer_Tick(object sender, EventArgs e)
{
if (otpListbox.SelectedItem is Item selected)
{
var otps = mOtpMan.GetAll();
var otp = otps.FirstOrDefault(o => o.Id == selected.Id);
if (otp != default)
{
long currentTime = DateTimeOffset.UtcNow.ToUnixTimeSeconds();
long lastUpdate = currentTime / otp.Duration;
long nextUpdate = (lastUpdate + 1) * otp.Duration;
int secondsRemaining = (int)(nextUpdate - currentTime);
// Only update if the TOTP code has changed or at the start of a new period
if (secondsRemaining == otp.Duration || string.IsNullOrEmpty(otpCodeLabel.Text))
{
UpdateOtpCode(otp);
}
else
{
// Update countdown without regenerating TOTP code
otpCountdownLabel.Text = cultureInfo.Name == mJpLang ? $"{secondsRemaining}秒" : $"{secondsRemaining}s";
otpCountdownProgress.Value = secondsRemaining;
}
}
else
{
otpCodeLabel.Text = string.Empty;
otpCountdownLabel.Text = string.Empty;
}
}
else
{
otpCodeLabel.Text = string.Empty;
otpCountdownLabel.Text = string.Empty;
}
}
private void ClearPasswordFields()
{
pwWebsiteTextbox.Text = string.Empty;
pwUsernameTextbox.Text = string.Empty;
pwPasswordTextbox.Text = string.Empty;
pwNotesTextbox.Text = string.Empty;
pwAddButton.Enabled = true;
pwEditButton.Enabled = false;
pwDeleteButton.Enabled = false;
pwCopyUsernameButton.Enabled = false;
pwCopyPasswordButton.Enabled = false;
pwShowButton.Enabled = false;
pwDoneButton.Enabled = false;
}
private void ClearOtpFields()
{
otpWebsiteTextbox1.Text = string.Empty;
otpWebsiteTextbox2.Text = string.Empty;
otpAuthTextbox.Text = string.Empty;
otpSecretTextbox.Text = string.Empty;
otpIssuerTextbox.Text = string.Empty;
otpAlgorithmCombobox.SelectedIndex = 0;
otpDigitsNumeric.Value = 6;
otpDurationNumeric.Value = 30;
otpCodeLabel.Text = string.Empty;
otpCountdownLabel.Text = string.Empty;
otpAddButton.Enabled = true;
otpAddLegacyButton.Enabled = true;
otpEditButton.Enabled = false;
otpDeleteButton.Enabled = false;
otpCopyButton.Enabled = false;
otpDoneButton.Enabled = false;
otpCountdownProgress.Value = 0;
}
private void ClearPinFields()
{
pinWebsiteTextbox.Text = string.Empty;
pinCodeTextbox.Text = string.Empty;
pinNoteTextbox.Text = string.Empty;
pinAddButton.Enabled = true;
pinEditButton.Enabled = false;
pinDeleteButton.Enabled = false;
pinCopyButton.Enabled = false;
pinShowButton.Enabled = false;
pinDoneButton.Enabled = false;
}
private void ClearNoteFields()
{
noteTitleTextbox.Text = string.Empty;
noteTextbox.Text = string.Empty;
noteTextbox.Enabled = false;
noteAddEditButton.Text = cultureInfo.Name == mJpLang ? "追加" : "Add";
noteDeleteButton.Enabled = false;
noteDoneButton.Enabled = false;
noteSaveButton.Enabled = false;
}
private void ClearQaFields()
{
qaWebsiteTextbox.Text = string.Empty;
qaQuestionTextbox.Text = string.Empty;
qaAnswerTextbox.Text = string.Empty;
qaNoteTextbox.Text = string.Empty;
qaAddButton.Enabled = true;
qaEditButton.Enabled = false;
qaDeleteButton.Enabled = false;
qaCopyButton.Enabled = false;
qaShowButton.Enabled = false;
qaDoneButton.Enabled = false;
}
private void ClearCcFields()
{
ccBrandCombobox.SelectedIndex = 0;
ccNumberTextbox.Text = string.Empty;
ccExpirationTextbox.Text = string.Empty;
ccCvcTextbox.Text = string.Empty;
ccHolderTextbox.Text = string.Empty;
ccNotesTextbox.Text = string.Empty;
ccAddButton.Enabled = true;
ccEditButton.Enabled = false;
ccDeleteButton.Enabled = false;
ccShowButton.Enabled = false;
ccDoneButton.Enabled = false;
}
private void ClearCryptoFields()
{
cryptoCurrencyCombobox.SelectedIndex = 0;
cryptoNameTextbox.Text = string.Empty;
cryptoAddressTextbox.Text = string.Empty;
cryptoSeedTextbox.Text = string.Empty;
cryptoViewkeyTextbox.Text = string.Empty;
cryptoSpendkeyTextbox.Text = string.Empty;
cryptoHeightTextbox.Text = string.Empty;
cryptoPasswordTextbox.Text = string.Empty;
cryptoNotesTextbox.Text = string.Empty;
cryptoAddButton.Enabled = true;
cryptoEditButton.Enabled = false;
cryptoDeleteButton.Enabled = false;
cryptoShowButton.Enabled = false;
cryptoDoneButton.Enabled = false;
}
private void LoadPasswords(string keyword = "")
{
pwListbox.Items.Clear();
var passwords = mPassMan.GetAll(keyword);
foreach (var pwd in passwords)
{
pwListbox.Items.Add(new Item(pwd.Id, $"{pwd.Website}/{pwd.Username}"));
}
}
private void LoadOtps(string keyword = "")
{
otpListbox.Items.Clear();
try
{
var otps = mOtpMan.GetAll(keyword);
foreach (var otp in otps)
{
otpListbox.Items.Add(new Item(otp.Id, $"{otp.Website} ({otp.Issuer})"));
}
if (otps.Count == 0)
{
string mes = cultureInfo.Name == mJpLang
? "データベースにOTPを見つけられませんでした。"
: "No OTPs found in the database.";
string tit = cultureInfo.Name == mJpLang
? "注意"
: "Warning";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Warning);
}
}
catch (Exception ex)
{
string mes = cultureInfo.Name == mJpLang
? $"OTPの読み込みに失敗{ex.Message}"
: $"Failed to load OTPs: {ex.Message}";
string tit = cultureInfo.Name == mJpLang
? "エラー"
: "Error";
MessageBox.Show(mes, tit, MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void LoadPins(string keyword = "")
{
pinListbox.Items.Clear();
var pins = mPinMan.GetAll(keyword);
foreach (var pin in pins)
{
pinListbox.Items.Add(new Item(pin.Id, $"{pin.Website}"));
}
}
private void LoadNotes(string keyword = "")
{
noteListbox.Items.Clear();
var notes = mNoteMan.GetAll(keyword);
foreach (var note in notes)
{
noteListbox.Items.Add(new Item(note.Id, $"{note.Name}"));
}
}
private void LoadQas(string keyword = "")
{
qaListbox.Items.Clear();
var qas = mQaMan.GetAll(keyword);
foreach (var qa in qas)
{
qaListbox.Items.Add(new Item(qa.Id, $"{qa.Website}/{qa.Question}"));
}
}
private void LoadCcs(string keyword = "")
{
ccListbox.Items.Clear();
var ccs = mCcMan.GetAll(keyword);
foreach (var cc in ccs)
{
ccListbox.Items.Add(new Item(cc.Id, $"{cc.Brand}/{cc.Holdername} ({cc.Expiration})"));
}
}
private void LoadCryptos(string keyword = "")
{
cryptoListbox.Items.Clear();
var cryptos = mCryptoMan.GetAll(keyword);
foreach (var crypto in cryptos)
{
cryptoListbox.Items.Add(new Item(crypto.Id, $"{crypto.Currency}/{crypto.Name}"));
}
}
private void UpdateOtpCode((int Id, string Website, string Secret, string Issuer, string Algorithm, int Duration, int Digits, string Note) otp)
{
try
{
var (code, error) = mOtpMan.GenerateTotp(otp.Secret, otp.Digits, otp.Algorithm, otp.Duration);
if (!string.IsNullOrEmpty(error))
{
otpCodeLabel.Text = cultureInfo.Name == mJpLang ? $"エラー:{error}" : $"Error: {error}";
otpCountdownLabel.Text = string.Empty;
}
else
{
otpCodeLabel.Text = code;
long currentTime = DateTimeOffset.UtcNow.ToUnixTimeSeconds();
int secondsRemaining = otp.Duration - (int)(currentTime % otp.Duration);
otpCountdownLabel.Text = cultureInfo.Name == mJpLang ? $"{secondsRemaining}秒" : $"{secondsRemaining}s";
otpCountdownProgress.Maximum = otp.Duration;
otpCountdownProgress.Value = secondsRemaining;
}
}
catch (Exception ex)
{
otpCodeLabel.Text = cultureInfo.Name == mJpLang ? $"エラー:{ex.Message}" : $"Error: {ex.Message}";
otpCountdownLabel.Text = string.Empty;
}
}
private class Item
{
public int Id { get; }
public string DisplayText { get; }
public Item(int id, string displayText)
{
Id = id;
DisplayText = displayText;
}
public override string ToString() => DisplayText;
}
}
}