Compare commits

...

13 Commits

12 changed files with 2383 additions and 1796 deletions

View File

@ -3,7 +3,9 @@ Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 17 # Visual Studio Version 17
VisualStudioVersion = 17.6.33815.320 VisualStudioVersion = 17.6.33815.320
MinimumVisualStudioVersion = 10.0.40219.1 MinimumVisualStudioVersion = 10.0.40219.1
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "FireWalletLite", "FireWalletLite\FireWalletLite.csproj", "{A375882A-CB5E-4268-A6CC-106B270EE200}" Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "FireWalletLite", "FireWalletLite\FireWalletLite.csproj", "{A375882A-CB5E-4268-A6CC-106B270EE200}"
EndProject
Project("{54435603-DBB4-11D2-8724-00A0C9A8B90C}") = "Installer", "Installer\Installer.vdproj", "{6D6023A9-C523-4DC2-9529-13B03B16A116}"
EndProject EndProject
Global Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution GlobalSection(SolutionConfigurationPlatforms) = preSolution
@ -15,6 +17,8 @@ Global
{A375882A-CB5E-4268-A6CC-106B270EE200}.Debug|Any CPU.Build.0 = Debug|Any CPU {A375882A-CB5E-4268-A6CC-106B270EE200}.Debug|Any CPU.Build.0 = Debug|Any CPU
{A375882A-CB5E-4268-A6CC-106B270EE200}.Release|Any CPU.ActiveCfg = Release|Any CPU {A375882A-CB5E-4268-A6CC-106B270EE200}.Release|Any CPU.ActiveCfg = Release|Any CPU
{A375882A-CB5E-4268-A6CC-106B270EE200}.Release|Any CPU.Build.0 = Release|Any CPU {A375882A-CB5E-4268-A6CC-106B270EE200}.Release|Any CPU.Build.0 = Release|Any CPU
{6D6023A9-C523-4DC2-9529-13B03B16A116}.Debug|Any CPU.ActiveCfg = Debug
{6D6023A9-C523-4DC2-9529-13B03B16A116}.Release|Any CPU.ActiveCfg = Release
EndGlobalSection EndGlobalSection
GlobalSection(SolutionProperties) = preSolution GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE HideSolutionNode = FALSE

View File

@ -2,296 +2,286 @@
using FireWallet; using FireWallet;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
namespace FireWalletLite namespace FireWalletLite;
public partial class DomainForm : Form
{ {
public partial class DomainForm : Form private readonly string Domain;
private readonly MainForm Main;
public DomainForm(MainForm main, string domain)
{ {
private MainForm Main; InitializeComponent();
private string Domain; Main = main;
public DomainForm(MainForm main, string domain) Domain = domain;
Text = domain + "/";
// Theme form
BackColor = ColorTranslator.FromHtml(main.Theme["background"]);
ForeColor = ColorTranslator.FromHtml(main.Theme["foreground"]);
foreach (Control control in Controls) main.ThemeControl(control);
labelName.Text = domain + "/";
}
private void buttonExplorer_Click(object sender, EventArgs e)
{
var psi = new ProcessStartInfo
{ {
InitializeComponent(); FileName = Main.DomainExplorer + Domain,
this.Main = main; UseShellExecute = true
this.Domain = domain; };
Text = domain + "/"; Process.Start(psi);
// Theme form }
BackColor = ColorTranslator.FromHtml(main.Theme["background"]);
ForeColor = ColorTranslator.FromHtml(main.Theme["foreground"]); private void DomainForm_Load(object sender, EventArgs e)
foreach (Control control in Controls) {
{ if (!File.Exists(Main.dir + "domains.json")) return;
main.ThemeControl(control);
} var domains = JArray.Parse(File.ReadAllText(Main.dir + "domains.json"));
labelName.Text = domain + "/"; foreach (JObject domain in domains)
if (domain["name"].ToString() == Domain)
if (domain.ContainsKey("status"))
switch (domain["status"].ToString())
{
case "transferring":
buttonFinalize.Visible = true;
buttonCancel.Visible = true;
buttonTransfer.Visible = false;
textBoxTransferAddress.Visible = false;
break;
case "closed":
buttonCancel.Visible = false;
buttonFinalize.Visible = false;
break;
}
}
private async void buttonRenew_Click(object sender, EventArgs e)
{
var path = "wallet/" + Main.Account + "/renewal";
var content = "{\"passphrase\": \"" + Main.Password + "\", \"name\": \"" + Domain +
"\", \"broadcast\": true, \"sign\": true}";
var response = await Main.APIPost(path, true, content);
if (response == "Error")
{
var notify = new NotifyForm("Error renewing domain");
notify.ShowDialog();
notify.Dispose();
return;
} }
private void buttonExplorer_Click(object sender, EventArgs e) var jObject = JObject.Parse(response);
if (jObject.ContainsKey("hash"))
{ {
ProcessStartInfo psi = new ProcessStartInfo var txid = jObject["hash"].ToString();
{ var notify = new NotifyForm("Renew sent", "Explorer", Main.TXExplorer + txid);
FileName = Main.DomainExplorer + Domain, notify.ShowDialog();
UseShellExecute = true notify.Dispose();
}; AddDomainInfo("closed");
Process.Start(psi); }
else
{
var notify = new NotifyForm("Error renewing domain");
notify.ShowDialog();
notify.Dispose();
}
}
private async void buttonTransfer_Click(object sender, EventArgs e)
{
var address = textBoxTransferAddress.Text;
var valid = await Main.ValidAddress(address);
if (!valid)
{
var notify = new NotifyForm("Invalid address");
notify.ShowDialog();
notify.Dispose();
return;
} }
private void DomainForm_Load(object sender, EventArgs e) var path = "wallet/" + Main.Account + "/transfer";
var content = "{\"passphrase\": \"" + Main.Password + "\", \"name\": \"" + Domain +
"\", \"broadcast\": true, \"sign\": true, \"address\": \"" + address + "\"}";
var response = await Main.APIPost(path, true, content);
if (response == "Error")
{ {
if (!File.Exists(Main.dir + "domains.json")) return; var notify = new NotifyForm("Error transferring domain");
notify.ShowDialog();
notify.Dispose();
return;
}
JArray domains = JArray.Parse(File.ReadAllText(Main.dir + "domains.json")); var jObject = JObject.Parse(response);
if (jObject.ContainsKey("hash"))
{
var txid = jObject["hash"].ToString();
var notify = new NotifyForm("Transferred domain", "Explorer", Main.TXExplorer + txid);
notify.ShowDialog();
notify.Dispose();
AddDomainInfo("transferring");
}
else
{
var notify = new NotifyForm("Error transferring domain");
notify.ShowDialog();
notify.Dispose();
}
}
private async void buttonFinalize_Click(object sender, EventArgs e)
{
var path = "wallet/" + Main.Account + "/finalize";
var content = "{\"passphrase\": \"" + Main.Password + "\", \"name\": \"" + Domain +
"\", \"broadcast\": true, \"sign\": true}";
var response = await Main.APIPost(path, true, content);
if (response == "Error")
{
var notify = new NotifyForm("Error finalizing transfer");
notify.ShowDialog();
notify.Dispose();
return;
}
var jObject = JObject.Parse(response);
if (jObject.ContainsKey("hash"))
{
var txid = jObject["hash"].ToString();
var notify = new NotifyForm("Finalized domain", "Explorer", Main.TXExplorer + txid);
notify.ShowDialog();
notify.Dispose();
AddDomainInfo("closed");
}
else
{
var notify = new NotifyForm("Error finalizing domain");
notify.ShowDialog();
notify.Dispose();
}
}
private async void buttonCancel_Click(object sender, EventArgs e)
{
var path = "wallet/" + Main.Account + "/cancel";
var content = "{\"passphrase\": \"" + Main.Password + "\", \"name\": \"" + Domain +
"\", \"broadcast\": true, \"sign\": true}";
var response = await Main.APIPost(path, true, content);
if (response == "Error")
{
var notify = new NotifyForm("Error cancelling transfer");
notify.ShowDialog();
notify.Dispose();
return;
}
var jObject = JObject.Parse(response);
if (jObject.ContainsKey("hash"))
{
var txid = jObject["hash"].ToString();
var notify = new NotifyForm("Canceled transfer", "Explorer", Main.TXExplorer + txid);
notify.ShowDialog();
notify.Dispose();
AddDomainInfo("closed");
}
else
{
var notify = new NotifyForm("Error cancelling transfer");
notify.ShowDialog();
notify.Dispose();
}
}
private void AddDomainInfo(string status)
{
if (File.Exists(Main.dir + "domains.json"))
{
var found = false;
var domains = JArray.Parse(File.ReadAllText(Main.dir + "domains.json"));
foreach (JObject domain in domains) foreach (JObject domain in domains)
{
if (domain["name"].ToString() == Domain) if (domain["name"].ToString() == Domain)
{ {
found = true;
if (domain.ContainsKey("status")) if (domain.ContainsKey("status"))
{ domain["status"] = status;
switch (domain["status"].ToString()) else
{ domain.Add("status", status);
case "transferring":
buttonFinalize.Visible = true;
buttonCancel.Visible = true;
buttonTransfer.Visible = false;
textBoxTransferAddress.Visible = false;
break;
case "closed":
buttonCancel.Visible = false;
buttonFinalize.Visible = false;
break;
}
}
}
}
}
private async void buttonRenew_Click(object sender, EventArgs e)
{
string content = "{\"method\": \"renew\", \"params\": [\"" + Domain + "\"]}";
string response = await Main.APIPost("", true, content);
if (response == "Error")
{
NotifyForm notify = new NotifyForm("Error renewing domain");
notify.ShowDialog();
notify.Dispose();
return;
}
JObject jObject = JObject.Parse(response);
if (jObject.ContainsKey("result"))
{
Main.AddLog(jObject["result"].ToString());
JObject result = (JObject)jObject["result"];
if (result.ContainsKey("txid"))
{
string txid = result["txid"].ToString();
NotifyForm notify = new NotifyForm("Renewed domain", "Explorer", Main.TXExplorer + txid);
notify.ShowDialog();
notify.Dispose();
}
else
{
NotifyForm notify = new NotifyForm("Error renewing domain");
notify.ShowDialog();
notify.Dispose();
}
}
else
{
NotifyForm notify = new NotifyForm("Error renewing domain");
notify.ShowDialog();
notify.Dispose();
Main.AddLog(jObject.ToString());
}
}
private async void buttonTransfer_Click(object sender, EventArgs e)
{
string address = textBoxTransferAddress.Text;
bool valid = await Main.ValidAddress(address);
if (!valid)
{
NotifyForm notify = new NotifyForm("Invalid address");
notify.ShowDialog();
notify.Dispose();
return;
}
string path = "wallet/" + Main.Account + "/transfer";
string content = "{\"passphrase\": \"" + Main.Password + "\", \"name\": \"" + Domain + "\", \"broadcast\": true, \"sign\": true, \"address\": \"" + address + "\"}";
string response = await Main.APIPost(path, true, content);
if (response == "Error")
{
NotifyForm notify = new NotifyForm("Error transferring domain");
notify.ShowDialog();
notify.Dispose();
return;
}
JObject jObject = JObject.Parse(response);
if (jObject.ContainsKey("hash"))
{
string txid = jObject["hash"].ToString();
NotifyForm notify = new NotifyForm("Transferred domain", "Explorer", Main.TXExplorer + txid);
notify.ShowDialog();
notify.Dispose();
AddDomainInfo("transferring");
}
else
{
NotifyForm notify = new NotifyForm("Error transferring domain");
notify.ShowDialog();
notify.Dispose();
}
}
private void buttonFinalize_Click(object sender, EventArgs e)
{
string path = "wallet/" + Main.Account + "/finalize";
string content = "{\"passphrase\": \"" + Main.Password + "\", \"name\": \"" + Domain + "\", \"broadcast\": true, \"sign\": true}";
string response = Main.APIPost(path, true, content).Result;
if (response == "Error")
{
NotifyForm notify = new NotifyForm("Error finalizing transfer");
notify.ShowDialog();
notify.Dispose();
return;
}
JObject jObject = JObject.Parse(response);
if (jObject.ContainsKey("hash"))
{
string txid = jObject["hash"].ToString();
NotifyForm notify = new NotifyForm("Finalized domain", "Explorer", Main.TXExplorer + txid);
notify.ShowDialog();
notify.Dispose();
AddDomainInfo("closed");
}
else
{
NotifyForm notify = new NotifyForm("Error finalizing domain");
notify.ShowDialog();
notify.Dispose();
}
}
private void buttonCancel_Click(object sender, EventArgs e)
{
string path = "wallet/" + Main.Account + "/cancel";
string content = "{\"passphrase\": \"" + Main.Password + "\", \"name\": \"" + Domain + "\", \"broadcast\": true, \"sign\": true}";
string response = Main.APIPost(path, true, content).Result;
if (response == "Error")
{
NotifyForm notify = new NotifyForm("Error cancelling transfer");
notify.ShowDialog();
notify.Dispose();
return;
}
JObject jObject = JObject.Parse(response);
if (jObject.ContainsKey("hash"))
{
string txid = jObject["hash"].ToString();
NotifyForm notify = new NotifyForm("Canceled transfer", "Explorer", Main.TXExplorer + txid);
notify.ShowDialog();
notify.Dispose();
AddDomainInfo("closed");
}
else
{
NotifyForm notify = new NotifyForm("Error cancelling transfer");
notify.ShowDialog();
notify.Dispose();
}
}
private void AddDomainInfo(string status)
{
if (File.Exists(Main.dir + "domains.json"))
{
bool found = false;
JArray domains = JArray.Parse(File.ReadAllText(Main.dir + "domains.json"));
foreach (JObject domain in domains)
{
if (domain["name"].ToString() == Domain)
{
found = true;
if (domain.ContainsKey("status"))
{
domain["status"] = status;
}
else
{
domain.Add("status", status);
}
}
} }
if (!found) if (!found)
{
JObject domain = new JObject();
domain["name"] = Domain;
domain["status"] = status;
domains.Add(domain);
}
File.WriteAllText(Main.dir + "domains.json", domains.ToString());
}
else
{ {
JArray domains = new JArray(); var domain = new JObject();
JObject domain = new JObject();
domain["name"] = Domain; domain["name"] = Domain;
domain["status"] = status; domain["status"] = status;
domains.Add(domain); domains.Add(domain);
File.WriteAllText(Main.dir + "domains.json", domains.ToString());
} }
File.WriteAllText(Main.dir + "domains.json", domains.ToString());
} }
else
private async void buttonSign_Click(object sender, EventArgs e)
{ {
if (buttonSign.Text == "Save") var domains = new JArray();
{ var domain = new JObject();
SaveFileDialog saveFileDialog = new SaveFileDialog(); domain["name"] = Domain;
saveFileDialog.Filter = "Text File|*.txt"; domain["status"] = status;
saveFileDialog.Title = "Save Signature"; domains.Add(domain);
if (saveFileDialog.ShowDialog() == DialogResult.OK) File.WriteAllText(Main.dir + "domains.json", domains.ToString());
{
JObject signature = new JObject();
signature["domain"] = Domain;
signature["message"] = textBoxSignMessage.Text;
signature["signature"] = textBoxSignature.Text;
signature["time"] = DateTime.Now.ToString();
File.WriteAllText(saveFileDialog.FileName, signature.ToString());
}
return;
}
if (textBoxSignMessage.Text == "")
{
NotifyForm notify = new NotifyForm("Enter a message to sign");
notify.ShowDialog();
notify.Dispose();
return;
}
string content = "{\"method\": \"signmessagewithname\", \"params\": [\"" + Domain + "\", \"" + textBoxSignMessage.Text + "\"]}";
string response = await Main.APIPost("", true, content);
if (response == "Error")
{
NotifyForm notify = new NotifyForm("Error signing message");
notify.ShowDialog();
notify.Dispose();
return;
}
JObject jObject = JObject.Parse(response);
if (jObject.ContainsKey("result"))
{
textBoxSignature.Text = jObject["result"].ToString();
buttonSign.Text = "Save";
}
else
{
Main.AddLog(response);
NotifyForm notify = new NotifyForm("Error signing message");
notify.ShowDialog();
notify.Dispose();
}
}
private void textBoxSignMessage_TextChanged(object sender, EventArgs e)
{
buttonSign.Text = "Sign";
} }
} }
}
private async void buttonSign_Click(object sender, EventArgs e)
{
if (buttonSign.Text == "Save")
{
var saveFileDialog = new SaveFileDialog();
saveFileDialog.Filter = "Text File|*.txt";
saveFileDialog.Title = "Save Signature";
if (saveFileDialog.ShowDialog() == DialogResult.OK)
{
var signature = new JObject();
signature["domain"] = Domain;
signature["message"] = textBoxSignMessage.Text;
signature["signature"] = textBoxSignature.Text;
signature["time"] = DateTime.Now.ToString();
File.WriteAllText(saveFileDialog.FileName, signature.ToString());
}
return;
}
if (textBoxSignMessage.Text == "")
{
var notify = new NotifyForm("Enter a message to sign");
notify.ShowDialog();
notify.Dispose();
return;
}
var content = "{\"method\": \"signmessagewithname\", \"params\": [\"" + Domain + "\", \"" +
textBoxSignMessage.Text + "\"]}";
var response = await Main.APIPost("", true, content);
if (response == "Error")
{
var notify = new NotifyForm("Error signing message");
notify.ShowDialog();
notify.Dispose();
return;
}
var jObject = JObject.Parse(response);
if (jObject.ContainsKey("result"))
{
textBoxSignature.Text = jObject["result"].ToString();
buttonSign.Text = "Save";
}
else
{
Main.AddLog(response);
var notify = new NotifyForm("Error signing message");
notify.ShowDialog();
notify.Dispose();
}
}
private void textBoxSignMessage_TextChanged(object sender, EventArgs e)
{
buttonSign.Text = "Sign";
}
}

View File

@ -1,59 +1,56 @@
using FireWallet; using FireWallet;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
namespace FireWalletLite namespace FireWalletLite;
public partial class FirstLoginForm : Form
{ {
public partial class FirstLoginForm : Form private readonly MainForm main;
private string seedPhrase;
public FirstLoginForm(string seedPhrase, MainForm mainForm)
{ {
String seedPhrase; InitializeComponent();
MainForm main; this.seedPhrase = seedPhrase;
public FirstLoginForm(string seedPhrase, MainForm mainForm) main = mainForm;
{ // Theme form
InitializeComponent(); BackColor = ColorTranslator.FromHtml(mainForm.Theme["background"]);
this.seedPhrase = seedPhrase; ForeColor = ColorTranslator.FromHtml(mainForm.Theme["foreground"]);
this.main = mainForm; foreach (Control control in Controls) mainForm.ThemeControl(control);
// Theme form textBoxSeed.Text = seedPhrase;
this.BackColor = ColorTranslator.FromHtml(mainForm.Theme["background"]);
this.ForeColor = ColorTranslator.FromHtml(mainForm.Theme["foreground"]);
foreach (Control control in Controls)
{
mainForm.ThemeControl(control);
}
textBoxSeed.Text = seedPhrase;
}
private async void Start_Click(object sender, EventArgs e)
{
if (textBoxPassword.Text.Length < 8)
{
NotifyForm notifyForm = new NotifyForm("Please choose a longer password!");
notifyForm.ShowDialog();
notifyForm.Dispose();
return;
}
if (textBoxPassword.Text != textBoxPassword2.Text)
{
NotifyForm notifyForm = new NotifyForm("Passwords do not match!");
notifyForm.ShowDialog();
notifyForm.Dispose();
return;
}
// Encrypt wallet
string content = "{\"method\":\"encryptwallet\",\"params\":[\"" + textBoxPassword.Text + "\"]}";
string response = await main.APIPost("",true,content);
main.AddLog("Encrypt wallet: " + response);
JObject jObject = JObject.Parse(response);
if (jObject["error"].ToString() != "")
{
NotifyForm notifyForm = new NotifyForm("Error encrypting wallet: " + jObject["error"].ToString());
notifyForm.ShowDialog();
notifyForm.Dispose();
return;
} else
{
this.Close();
}
}
} }
}
private async void Start_Click(object sender, EventArgs e)
{
if (textBoxPassword.Text.Length < 8)
{
var notifyForm = new NotifyForm("Please choose a longer password!");
notifyForm.ShowDialog();
notifyForm.Dispose();
return;
}
if (textBoxPassword.Text != textBoxPassword2.Text)
{
var notifyForm = new NotifyForm("Passwords do not match!");
notifyForm.ShowDialog();
notifyForm.Dispose();
return;
}
// Encrypt wallet
var content = "{\"method\":\"encryptwallet\",\"params\":[\"" + textBoxPassword.Text + "\"]}";
var response = await main.APIPost("", true, content);
main.AddLog("Encrypt wallet: " + response);
var jObject = JObject.Parse(response);
if (jObject["error"].ToString() != "")
{
var notifyForm = new NotifyForm("Error encrypting wallet: " + jObject["error"]);
notifyForm.ShowDialog();
notifyForm.Dispose();
return;
}
Close();
}
}

View File

@ -2,237 +2,248 @@ using System.Diagnostics;
using System.Text.RegularExpressions; using System.Text.RegularExpressions;
using FireWallet; using FireWallet;
namespace FireWalletLite namespace FireWalletLite;
public partial class Loader : Form
{ {
public partial class Loader : Form #region Constants
private readonly MainForm mainForm = new();
private readonly bool hideScreen = true; // Hide screen or not (for debug)
private readonly Process HSDProcess;
#endregion
public Loader()
{ {
#region Constants InitializeComponent();
MainForm mainForm = new MainForm();
bool hideScreen = true;
Process HSDProcess;
#endregion
public Loader() var splashScreen = new SplashScreen(false);
splashScreen.Show();
Application.DoEvents();
var start = DateTime.Now;
// Install and load node
var dir = mainForm.dir;
HSDProcess = new Process();
if (!Directory.Exists(dir)) Environment.Exit(1);
var hsdPath = dir + "hsd\\bin\\hsd.exe";
if (!Directory.Exists(dir + "hsd"))
{ {
InitializeComponent(); var repositoryUrl = "https://github.com/handshake-org/hsd.git";
var destinationPath = dir + "hsd";
CloneRepository(repositoryUrl, destinationPath);
}
SplashScreen splashScreen = new SplashScreen(false); // Start HSD
splashScreen.Show(); HSDProcess.StartInfo.RedirectStandardInput = true;
HSDProcess.StartInfo.RedirectStandardOutput = false;
HSDProcess.StartInfo.UseShellExecute = false;
HSDProcess.StartInfo.FileName = "node.exe";
HSDProcess.StartInfo.Arguments = dir + "hsd\\bin\\hsd --agent=FireWallet --spv --prefix " + dir + "\\hsd_data";
HSDProcess.StartInfo.CreateNoWindow = hideScreen;
if (hideScreen)
{
HSDProcess.StartInfo.RedirectStandardError = true;
// Send errors to log
HSDProcess.ErrorDataReceived += (sender, e) => mainForm.AddLog("HSD Error: " + e.Data);
}
else
{
HSDProcess.StartInfo.RedirectStandardError = false;
}
HSDProcess.Start();
while ((DateTime.Now - start).TotalSeconds < 5)
{
Thread.Sleep(10);
Application.DoEvents(); Application.DoEvents();
DateTime start = DateTime.Now; }
// Install and load node
string dir = mainForm.dir; splashScreen.CloseSplash();
HSDProcess = new Process(); while (!splashScreen.IsClosed)
if (!Directory.Exists(dir)) Environment.Exit(1); {
string hsdPath = dir + "hsd\\bin\\hsd.exe"; Thread.Sleep(10);
if (!Directory.Exists(dir + "hsd")) Application.DoEvents();
}
splashScreen.Dispose();
mainForm.Show();
}
#region Git
public void CloneRepository(string repositoryUrl, string destinationPath)
{
try
{
// Check if git is installed
var testInstalled = new Process();
testInstalled.StartInfo.FileName = "git";
testInstalled.StartInfo.Arguments = "-v";
testInstalled.StartInfo.RedirectStandardOutput = true;
testInstalled.StartInfo.UseShellExecute = false;
testInstalled.StartInfo.CreateNoWindow = true;
testInstalled.Start();
var outputInstalled = testInstalled.StandardOutput.ReadToEnd();
testInstalled.WaitForExit();
if (!outputInstalled.Contains("git version"))
{ {
string repositoryUrl = "https://github.com/handshake-org/hsd.git"; mainForm.AddLog("Git is not installed");
string destinationPath = dir + "hsd"; var notifyForm = new NotifyForm("Git is not installed\nPlease install it to install HSD dependencies",
CloneRepository(repositoryUrl, destinationPath); "Install", "https://git-scm.com/download/win");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(21);
return;
} }
// Start HSD
HSDProcess.StartInfo.RedirectStandardInput = true; // Check if node installed
HSDProcess.StartInfo.RedirectStandardOutput = false; testInstalled = new Process();
HSDProcess.StartInfo.UseShellExecute = false; testInstalled.StartInfo.FileName = "node";
HSDProcess.StartInfo.FileName = "node.exe"; testInstalled.StartInfo.Arguments = "-v";
HSDProcess.StartInfo.Arguments = dir + "hsd\\bin\\hsd --agent=FireWallet --spv --prefix " + dir + "\\hsd_data"; testInstalled.StartInfo.RedirectStandardOutput = true;
HSDProcess.StartInfo.CreateNoWindow = hideScreen; testInstalled.StartInfo.UseShellExecute = false;
if (hideScreen) testInstalled.StartInfo.CreateNoWindow = true;
testInstalled.Start();
outputInstalled = testInstalled.StandardOutput.ReadToEnd();
testInstalled.WaitForExit();
if (!outputInstalled.Contains("v"))
{ {
HSDProcess.StartInfo.RedirectStandardError = true; mainForm.AddLog("Node is not installed");
// Send errors to log var notifyForm = new NotifyForm("Node is not installed\nPlease install it to install HSD dependencies",
HSDProcess.ErrorDataReceived += (sender, e) => mainForm.AddLog("HSD Error: " + e.Data); "Install", "https://nodejs.org/en/download");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(22);
return;
}
// Check if npm installed
testInstalled = new Process();
testInstalled.StartInfo.FileName = "cmd.exe";
testInstalled.StartInfo.Arguments = "npm -v";
testInstalled.StartInfo.RedirectStandardOutput = true;
testInstalled.StartInfo.UseShellExecute = false;
testInstalled.StartInfo.CreateNoWindow = false;
testInstalled.Start();
// Wait 3 seconds and then kill
Thread.Sleep(3000);
testInstalled.Kill();
outputInstalled = testInstalled.StandardOutput.ReadToEnd();
testInstalled.WaitForExit();
if (Regex.IsMatch(outputInstalled, @"^\d+\.\d+\.\d+$"))
{
mainForm.AddLog("NPM is not installed");
mainForm.AddLog(outputInstalled);
var notifyForm = new NotifyForm("NPM is not installed\nPlease install it to install HSD dependencies",
"Install", "https://docs.npmjs.com/downloading-and-installing-node-js-and-npm");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(23);
return;
}
mainForm.AddLog("Prerequisites installed");
var startInfo = new ProcessStartInfo();
startInfo.FileName = "git";
startInfo.Arguments = $"clone {repositoryUrl} {destinationPath}";
if (repositoryUrl == "https://github.com/handshake-org/hsd.git")
startInfo.Arguments = $"clone --depth 1 --branch latest {repositoryUrl} {destinationPath}";
startInfo.RedirectStandardOutput = true;
startInfo.UseShellExecute = false;
startInfo.CreateNoWindow = hideScreen;
var process = new Process();
process.StartInfo = startInfo;
process.Start();
var output = process.StandardOutput.ReadToEnd();
process.WaitForExit();
while (!process.HasExited) output += process.StandardOutput.ReadToEnd();
var psiNpmRunDist = new ProcessStartInfo
{
FileName = "cmd",
RedirectStandardInput = true,
WorkingDirectory = destinationPath,
CreateNoWindow = hideScreen
};
var pNpmRunDist = Process.Start(psiNpmRunDist);
pNpmRunDist.StandardInput.WriteLine("npm install & exit");
pNpmRunDist.WaitForExit();
}
catch (Exception ex)
{
mainForm.AddLog("Git/NPM Install FAILED");
mainForm.AddLog(ex.Message);
if (ex.Message.Contains("to start process 'git'"))
{
var notifyForm = new NotifyForm("Git is not installed\nPlease install it to install HSD dependencies",
"Install", "https://git-scm.com/download/win");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(21);
}
else if (ex.Message.Contains("to start process 'node'"))
{
var notifyForm = new NotifyForm("Node is not installed\nPlease install it to install HSD dependencies",
"Install", "https://nodejs.org/en/download");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(22);
}
else if (ex.Message.Contains("to start process 'npm'"))
{
var notifyForm = new NotifyForm("NPM is not installed\nPlease install it to install HSD dependencies",
"Install", "https://docs.npmjs.com/downloading-and-installing-node-js-and-npm");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(23);
} }
else else
{ {
HSDProcess.StartInfo.RedirectStandardError = false; var notifyForm = new NotifyForm("Git/NPM Install FAILED\nCheck logs for more details");
} notifyForm.ShowDialog();
HSDProcess.Start(); notifyForm.Dispose();
while ((DateTime.Now - start).TotalSeconds < 5)
{
Thread.Sleep(10);
Application.DoEvents();
}
splashScreen.CloseSplash();
while (!splashScreen.IsClosed)
{
Thread.Sleep(10);
Application.DoEvents();
}
splashScreen.Dispose();
mainForm.Show();
}
#region Git
public void CloneRepository(string repositoryUrl, string destinationPath)
{
try
{
// Check if git is installed
Process testInstalled = new Process();
testInstalled.StartInfo.FileName = "git";
testInstalled.StartInfo.Arguments = "-v";
testInstalled.StartInfo.RedirectStandardOutput = true;
testInstalled.StartInfo.UseShellExecute = false;
testInstalled.StartInfo.CreateNoWindow = true;
testInstalled.Start();
string outputInstalled = testInstalled.StandardOutput.ReadToEnd();
testInstalled.WaitForExit();
if (!outputInstalled.Contains("git version"))
{
mainForm.AddLog("Git is not installed");
NotifyForm notifyForm = new NotifyForm("Git is not installed\nPlease install it to install HSD dependencies", "Install", "https://git-scm.com/download/win");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(21);
return;
}
// Check if node installed
testInstalled = new Process();
testInstalled.StartInfo.FileName = "node";
testInstalled.StartInfo.Arguments = "-v";
testInstalled.StartInfo.RedirectStandardOutput = true;
testInstalled.StartInfo.UseShellExecute = false;
testInstalled.StartInfo.CreateNoWindow = true;
testInstalled.Start();
outputInstalled = testInstalled.StandardOutput.ReadToEnd();
testInstalled.WaitForExit();
if (!outputInstalled.Contains("v"))
{
mainForm.AddLog("Node is not installed");
NotifyForm notifyForm = new NotifyForm("Node is not installed\nPlease install it to install HSD dependencies", "Install", "https://nodejs.org/en/download");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(22);
return;
}
// Check if npm installed
testInstalled = new Process();
testInstalled.StartInfo.FileName = "cmd.exe";
testInstalled.StartInfo.Arguments = "npm -v";
testInstalled.StartInfo.RedirectStandardOutput = true;
testInstalled.StartInfo.UseShellExecute = false;
testInstalled.StartInfo.CreateNoWindow = false;
testInstalled.Start();
// Wait 3 seconds and then kill
Thread.Sleep(3000);
testInstalled.Kill();
outputInstalled = testInstalled.StandardOutput.ReadToEnd();
testInstalled.WaitForExit();
if (Regex.IsMatch(outputInstalled, @"^\d+\.\d+\.\d+$"))
{
mainForm.AddLog("NPM is not installed");
mainForm.AddLog(outputInstalled);
NotifyForm notifyForm = new NotifyForm("NPM is not installed\nPlease install it to install HSD dependencies", "Install", "https://docs.npmjs.com/downloading-and-installing-node-js-and-npm");
notifyForm.ShowDialog();
notifyForm.Dispose();
Environment.Exit(23);
return;
}
mainForm.AddLog("Prerequisites installed");
ProcessStartInfo startInfo = new ProcessStartInfo();
startInfo.FileName = "git";
startInfo.Arguments = $"clone {repositoryUrl} {destinationPath}";
if (repositoryUrl == "https://github.com/handshake-org/hsd.git")
{
startInfo.Arguments = $"clone --depth 1 --branch latest {repositoryUrl} {destinationPath}";
}
startInfo.RedirectStandardOutput = true;
startInfo.UseShellExecute = false;
startInfo.CreateNoWindow = hideScreen;
Process process = new Process();
process.StartInfo = startInfo;
process.Start();
string output = process.StandardOutput.ReadToEnd();
process.WaitForExit();
while (!process.HasExited)
{
output += process.StandardOutput.ReadToEnd();
}
var psiNpmRunDist = new ProcessStartInfo
{
FileName = "cmd",
RedirectStandardInput = true,
WorkingDirectory = destinationPath,
CreateNoWindow = hideScreen
};
var pNpmRunDist = Process.Start(psiNpmRunDist);
pNpmRunDist.StandardInput.WriteLine("npm install & exit");
pNpmRunDist.WaitForExit();
}
catch (Exception ex)
{
mainForm.AddLog("Git/NPM Install FAILED");
mainForm.AddLog(ex.Message);
if (ex.Message.Contains("to start process 'git'"))
{
NotifyForm notifyForm = new NotifyForm("Git needs to be installed\nCheck logs for more details");
notifyForm.ShowDialog();
notifyForm.Dispose();
}
else if (ex.Message.Contains("to start process 'node'"))
{
NotifyForm notifyForm = new NotifyForm("Node needs to be installed\nCheck logs for more details");
notifyForm.ShowDialog();
notifyForm.Dispose();
}
else if (ex.Message.Contains("to start process 'npm'"))
{
NotifyForm notifyForm = new NotifyForm("NPM needs to be installed\nCheck logs for more details");
notifyForm.ShowDialog();
notifyForm.Dispose();
}
else
{
NotifyForm notifyForm = new NotifyForm("Git/NPM Install FAILED\nCheck logs for more details");
notifyForm.ShowDialog();
notifyForm.Dispose();
}
Environment.Exit(24); Environment.Exit(24);
} }
} }
public bool CheckNodeInstalled()
{
try
{
// Create a new process to execute the 'node' command
Process process = new Process();
process.StartInfo.FileName = "node";
process.StartInfo.Arguments = "--version";
process.StartInfo.RedirectStandardOutput = true;
process.StartInfo.UseShellExecute = false;
process.StartInfo.CreateNoWindow = true;
// Start the process and read the output
process.Start();
string output = process.StandardOutput.ReadToEnd();
// Wait for the process to exit
process.WaitForExit();
// Check if the output contains a version number
return !string.IsNullOrEmpty(output);
}
catch (Exception)
{
// An exception occurred, indicating that 'node' is not installed or accessible
return false;
}
}
#endregion
} }
public bool CheckNodeInstalled()
{
try
{
// Create a new process to execute the 'node' command
var process = new Process();
process.StartInfo.FileName = "node";
process.StartInfo.Arguments = "--version";
process.StartInfo.RedirectStandardOutput = true;
process.StartInfo.UseShellExecute = false;
process.StartInfo.CreateNoWindow = true;
// Start the process and read the output
process.Start();
var output = process.StandardOutput.ReadToEnd();
// Wait for the process to exit
process.WaitForExit();
// Check if the output contains a version number
return !string.IsNullOrEmpty(output);
}
catch (Exception)
{
// An exception occurred, indicating that 'node' is not installed or accessible
return false;
}
}
#endregion
} }

File diff suppressed because it is too large Load Diff

View File

@ -1,266 +1,136 @@
using System.Diagnostics; using System.Diagnostics;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
namespace FireWallet namespace FireWallet;
public partial class NotifyForm : Form
{ {
public partial class NotifyForm : Form private bool allowClose = true;
private readonly string altLink;
private readonly bool Linkcopy;
public Dictionary<string, string> Theme { get; set; } = new()
{ {
string dir = Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData) + "\\FireWallet\\"; { "background", "#000000" },
Dictionary<string, string> theme; { "foreground", "#8e05c2"},
string altLink; { "background-alt", "#3e065f"},
bool Linkcopy; { "foreground-alt", "#ffffff"}
bool allowClose = true; };
public NotifyForm(string Message)
public NotifyForm(string Message)
{
InitializeComponent();
labelmessage.Text = Message;
altLink = "";
}
public NotifyForm(string Message, string altText, string altLink)
{
InitializeComponent();
labelmessage.Text = Message;
buttonALT.Text = altText;
buttonALT.Visible = true;
this.altLink = altLink;
buttonOK.Focus();
Linkcopy = false;
}
public NotifyForm(string Message, bool allowClose)
{
InitializeComponent();
labelmessage.Text = Message;
buttonOK.Focus();
Linkcopy = false;
buttonOK.Visible = allowClose;
allowClose = allowClose;
}
public NotifyForm(string Message, string altText, string altLink, bool Linkcopy)
{
InitializeComponent();
labelmessage.Text = Message;
buttonALT.Text = altText;
buttonALT.Visible = true;
this.altLink = altLink;
buttonOK.Focus();
this.Linkcopy = Linkcopy;
if (Linkcopy)
// Small font to fix more data
labelmessage.Font = new Font(labelmessage.Font.FontFamily, 10);
}
public void CloseNotification()
{
Close();
}
private void NotifyForm_Load(object sender, EventArgs e)
{
UpdateTheme();
}
private void OK_Click(object sender, EventArgs e)
{
allowClose = true;
Close();
}
private void buttonALT_Click(object sender, EventArgs e)
{
if (Linkcopy)
{ {
InitializeComponent(); // Copy link to clipboard
labelmessage.Text = Message; Clipboard.SetText(altLink);
altLink = ""; return;
}
public void CloseNotification()
{
this.Close();
}
public NotifyForm(string Message, string altText, string altLink)
{
InitializeComponent();
labelmessage.Text = Message;
buttonALT.Text = altText;
buttonALT.Visible = true;
this.altLink = altLink;
buttonOK.Focus();
Linkcopy = false;
}
public NotifyForm(string Message, bool allowClose)
{
InitializeComponent();
labelmessage.Text = Message;
buttonOK.Focus();
Linkcopy = false;
buttonOK.Visible = allowClose;
allowClose = allowClose;
} }
public NotifyForm(string Message, string altText, string altLink, bool Linkcopy) // Open link
var psi = new ProcessStartInfo
{ {
InitializeComponent(); FileName = altLink,
labelmessage.Text = Message; UseShellExecute = true
buttonALT.Text = altText; };
buttonALT.Visible = true; Process.Start(psi);
this.altLink = altLink; }
buttonOK.Focus();
this.Linkcopy = Linkcopy;
if (Linkcopy) private void NotifyForm_FormClosing(object sender, FormClosingEventArgs e)
{ {
// Small font to fix more data if (!allowClose) e.Cancel = true;
labelmessage.Font = new Font(labelmessage.Font.FontFamily, 10); }
}
#region Theming
private void UpdateTheme()
{
if (!Theme.ContainsKey("background") || !Theme.ContainsKey("background-alt") ||
!Theme.ContainsKey("foreground") || !Theme.ContainsKey("foreground-alt")) return;
// Apply Theme
BackColor = ColorTranslator.FromHtml(Theme["background"]);
// Foreground
ForeColor = ColorTranslator.FromHtml(Theme["foreground"]);
// Need to specify this for each groupbox to override the black text
foreach (Control c in Controls) ThemeControl(c);
}
private void ThemeControl(Control c)
{
if (c.GetType() == typeof(GroupBox) || c.GetType() == typeof(Panel))
{
c.ForeColor = ColorTranslator.FromHtml(Theme["foreground"]);
foreach (Control sub in c.Controls) ThemeControl(sub);
} }
#region Theming if (c.GetType() == typeof(TextBox) || c.GetType() == typeof(Button)
private void UpdateTheme() || c.GetType() == typeof(ComboBox) || c.GetType() == typeof(StatusStrip))
{ {
// Check if file exists c.ForeColor = ColorTranslator.FromHtml(Theme["foreground-alt"]);
if (!Directory.Exists(dir)) c.BackColor = ColorTranslator.FromHtml(Theme["background-alt"]);
{
CreateConfig(dir);
}
if (!File.Exists(dir + "theme.txt"))
{
CreateConfig(dir);
}
// Read file
StreamReader sr = new StreamReader(dir + "theme.txt");
theme = new Dictionary<string, string>();
while (!sr.EndOfStream)
{
string line = sr.ReadLine();
string[] split = line.Split(':');
theme.Add(split[0].Trim(), split[1].Trim());
}
sr.Dispose();
if (!theme.ContainsKey("background") || !theme.ContainsKey("background-alt") || !theme.ContainsKey("foreground") || !theme.ContainsKey("foreground-alt"))
{
return;
}
// Apply theme
this.BackColor = ColorTranslator.FromHtml(theme["background"]);
// Foreground
this.ForeColor = ColorTranslator.FromHtml(theme["foreground"]);
// Need to specify this for each groupbox to override the black text
foreach (Control c in Controls)
{
ThemeControl(c);
}
// Transparancy
applyTransparency(theme);
}
private void ThemeControl(Control c)
{
if (c.GetType() == typeof(GroupBox) || c.GetType() == typeof(Panel))
{
c.ForeColor = ColorTranslator.FromHtml(theme["foreground"]);
foreach (Control sub in c.Controls)
{
ThemeControl(sub);
}
}
if (c.GetType() == typeof(TextBox) || c.GetType() == typeof(Button)
|| c.GetType() == typeof(ComboBox) || c.GetType() == typeof(StatusStrip))
{
c.ForeColor = ColorTranslator.FromHtml(theme["foreground-alt"]);
c.BackColor = ColorTranslator.FromHtml(theme["background-alt"]);
}
}
private void applyTransparency(Dictionary<string, string> theme)
{
if (theme.ContainsKey("transparent-mode"))
{
switch (theme["transparent-mode"])
{
case "mica":
var accent = new AccentPolicy { AccentState = AccentState.ACCENT_ENABLE_BLURBEHIND };
var accentStructSize = Marshal.SizeOf(accent);
var accentPtr = Marshal.AllocHGlobal(accentStructSize);
Marshal.StructureToPtr(accent, accentPtr, false);
var data = new WindowCompositionAttributeData
{
Attribute = WindowCompositionAttribute.WCA_ACCENT_POLICY,
SizeOfData = accentStructSize,
Data = accentPtr
};
User32.SetWindowCompositionAttribute(Handle, ref data);
Marshal.FreeHGlobal(accentPtr);
break;
case "key":
if (theme.ContainsKey("transparency-key"))
{
switch (theme["transparency-key"])
{
case "alt":
this.TransparencyKey = ColorTranslator.FromHtml(theme["background-alt"]);
break;
case "main":
this.TransparencyKey = ColorTranslator.FromHtml(theme["background"]);
break;
default:
this.TransparencyKey = ColorTranslator.FromHtml(theme["transparency-key"]);
break;
}
}
break;
case "percent":
if (theme.ContainsKey("transparency-percent"))
{
Opacity = Convert.ToDouble(theme["transparency-percent"]) / 100;
}
break;
}
}
}
private void CreateConfig(string dir)
{
if (!Directory.Exists(dir))
{
Directory.CreateDirectory(dir);
}
StreamWriter sw = new StreamWriter(dir + "theme.txt");
sw.WriteLine("background: #000000");
sw.WriteLine("foreground: #8e05c2");
sw.WriteLine("background-alt: #3e065f");
sw.WriteLine("foreground-alt: #ffffff");
sw.WriteLine("transparent-mode: off");
sw.WriteLine("transparency-key: main");
sw.WriteLine("transparency-percent: 90");
sw.Dispose();
}
// Required for mica effect
internal enum AccentState
{
ACCENT_DISABLED = 0,
ACCENT_ENABLE_GRADIENT = 1,
ACCENT_ENABLE_TRANSPARENTGRADIENT = 2,
ACCENT_ENABLE_BLURBEHIND = 3,
ACCENT_INVALID_STATE = 4
}
internal enum WindowCompositionAttribute
{
WCA_ACCENT_POLICY = 19
}
[StructLayout(LayoutKind.Sequential)]
internal struct AccentPolicy
{
public AccentState AccentState;
public int AccentFlags;
public int GradientColor;
public int AnimationId;
}
[StructLayout(LayoutKind.Sequential)]
internal struct WindowCompositionAttributeData
{
public WindowCompositionAttribute Attribute;
public IntPtr Data;
public int SizeOfData;
}
internal static class User32
{
[DllImport("user32.dll")]
internal static extern int SetWindowCompositionAttribute(IntPtr hwnd, ref WindowCompositionAttributeData data);
}
#endregion
private void NotifyForm_Load(object sender, EventArgs e)
{
UpdateTheme();
}
private void OK_Click(object sender, EventArgs e)
{
allowClose = true;
this.Close();
}
private void buttonALT_Click(object sender, EventArgs e)
{
if (Linkcopy)
{
// Copy link to clipboard
Clipboard.SetText(altLink);
return;
}
// Open link
ProcessStartInfo psi = new ProcessStartInfo
{
FileName = altLink,
UseShellExecute = true
};
Process.Start(psi);
}
private void NotifyForm_FormClosing(object sender, FormClosingEventArgs e)
{
if (!allowClose) e.Cancel = true;
} }
} }
} #endregion
}

View File

@ -1,17 +1,16 @@
namespace FireWalletLite namespace FireWalletLite;
internal static class Program
{ {
internal static class Program /// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
private static void Main()
{ {
/// <summary> // To customize application configuration such as set high DPI settings or default font,
/// The main entry point for the application. // see https://aka.ms/applicationconfiguration.
/// </summary> ApplicationConfiguration.Initialize();
[STAThread] Application.Run(new Loader());
static void Main()
{
// To customize application configuration such as set high DPI settings or default font,
// see https://aka.ms/applicationconfiguration.
ApplicationConfiguration.Initialize();
Application.Run(new Loader());
}
} }
} }

View File

@ -1,42 +1,39 @@
using QRCoder; using QRCoder;
namespace FireWalletLite namespace FireWalletLite;
public partial class ReceiveForm : Form
{ {
public partial class ReceiveForm : Form private readonly string address;
private MainForm main;
public ReceiveForm(string address, MainForm main)
{ {
string address; InitializeComponent();
MainForm main; this.address = address;
public ReceiveForm(string address, MainForm main) this.main = main;
{ // Theme form
InitializeComponent(); BackColor = ColorTranslator.FromHtml(main.Theme["background"]);
this.address = address; ForeColor = ColorTranslator.FromHtml(main.Theme["foreground"]);
this.main = main; foreach (Control control in Controls) main.ThemeControl(control);
// Theme form textBoxReceive.Text = address;
this.BackColor = ColorTranslator.FromHtml(main.Theme["background"]); textBoxReceive.Left = (ClientSize.Width - textBoxReceive.Width) / 2;
this.ForeColor = ColorTranslator.FromHtml(main.Theme["foreground"]); label1.Left = (ClientSize.Width - label1.Width) / 2;
foreach (Control control in Controls) buttonCopy.Left = (ClientSize.Width - buttonCopy.Width) / 2;
{
main.ThemeControl(control);
}
textBoxReceive.Text = address;
textBoxReceive.Left = (this.ClientSize.Width - textBoxReceive.Width) / 2;
label1.Left = (this.ClientSize.Width - label1.Width) / 2;
buttonCopy.Left = (this.ClientSize.Width - buttonCopy.Width) / 2;
var qrcode = new QRCodeGenerator();
QRCodeGenerator qrcode = new QRCodeGenerator(); var qrData = qrcode.CreateQrCode(address, QRCodeGenerator.ECCLevel.Q);
QRCodeData qrData = qrcode.CreateQrCode(address, QRCodeGenerator.ECCLevel.Q); var qrCode = new QRCode(qrData);
QRCode qrCode = new QRCode(qrData); pictureBoxReceiveQR.Image = qrCode.GetGraphic(20, main.Theme["foreground"], main.Theme["background"]);
pictureBoxReceiveQR.Image = qrCode.GetGraphic(20, main.Theme["foreground"], main.Theme["background"]); pictureBoxReceiveQR.SizeMode = PictureBoxSizeMode.Zoom;
pictureBoxReceiveQR.SizeMode = PictureBoxSizeMode.Zoom; pictureBoxReceiveQR.Width = ClientSize.Width / 2;
pictureBoxReceiveQR.Width = this.ClientSize.Width / 2; pictureBoxReceiveQR.Height = ClientSize.Width / 2;
pictureBoxReceiveQR.Height = this.ClientSize.Width / 2; pictureBoxReceiveQR.Left = (ClientSize.Width - pictureBoxReceiveQR.Width) / 2;
pictureBoxReceiveQR.Left = (this.ClientSize.Width - pictureBoxReceiveQR.Width) / 2;
}
private void buttonCopy_Click(object sender, EventArgs e)
{
Clipboard.SetText(address);
}
} }
}
private void buttonCopy_Click(object sender, EventArgs e)
{
Clipboard.SetText(address);
}
}

View File

@ -1,106 +1,102 @@
using FireWallet; using FireWallet;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
namespace FireWalletLite namespace FireWalletLite;
public partial class SendForm : Form
{ {
public partial class SendForm : Form private readonly int fee = 1;
private readonly MainForm main;
private readonly decimal unlockedbalance;
public SendForm(decimal Unlockedbalance, MainForm main)
{ {
int fee = 1; InitializeComponent();
decimal unlockedbalance; this.main = main;
MainForm main; unlockedbalance = Unlockedbalance;
public SendForm(decimal Unlockedbalance, MainForm main)
{
InitializeComponent();
this.main = main;
this.unlockedbalance = Unlockedbalance;
// Theme form // Theme form
this.BackColor = ColorTranslator.FromHtml(main.Theme["background"]); BackColor = ColorTranslator.FromHtml(main.Theme["background"]);
this.ForeColor = ColorTranslator.FromHtml(main.Theme["foreground"]); ForeColor = ColorTranslator.FromHtml(main.Theme["foreground"]);
foreach (Control control in Controls) foreach (Control control in Controls) main.ThemeControl(control);
{
main.ThemeControl(control);
}
labelMax.Text = "Max: " + (unlockedbalance - fee).ToString() + " HNS"; labelMax.Text = "Max: " + (unlockedbalance - fee) + " HNS";
if (unlockedbalance < fee) if (unlockedbalance < fee) labelMax.Text = "Max: 0 HNS";
{ //buttonSend.Enabled = false;
labelMax.Text = "Max: 0 HNS"; // Allign controls
//buttonSend.Enabled = false; labelAddress.Left = (ClientSize.Width - labelAddress.Width) / 2;
} labelAmount.Left = (ClientSize.Width - labelAmount.Width) / 2;
textBoxAddress.Left = (ClientSize.Width - textBoxAddress.Width) / 2;
// Allign controls labelMax.Left = (ClientSize.Width - labelMax.Width) / 2;
labelAddress.Left = (this.ClientSize.Width - labelAddress.Width) / 2; textBoxAmount.Left = (ClientSize.Width - textBoxAmount.Width - labelHNSToken.Width - 10) / 2;
labelAmount.Left = (this.ClientSize.Width - labelAmount.Width) / 2; labelHNSToken.Left = textBoxAmount.Left + textBoxAmount.Width + 10;
textBoxAddress.Left = (this.ClientSize.Width - textBoxAddress.Width) / 2; buttonSend.Left = (ClientSize.Width - buttonSend.Width) / 2;
labelMax.Left = (this.ClientSize.Width - labelMax.Width) / 2;
textBoxAmount.Left = (this.ClientSize.Width - textBoxAmount.Width - labelHNSToken.Width - 10) / 2;
labelHNSToken.Left = textBoxAmount.Left + textBoxAmount.Width + 10;
buttonSend.Left = (this.ClientSize.Width - buttonSend.Width) / 2;
}
private async void buttonSend_Click(object sender, EventArgs e)
{
buttonSend.Enabled = false;
string address = textBoxAddress.Text;
if (textBoxAddress.Text.Substring(0,1) == "@")
{
// HIP-02 not supported yet
NotifyForm notify = new NotifyForm("HIP-02 not supported yet");
notify.ShowDialog();
notify.Dispose();
buttonSend.Enabled = true;
return;
}
bool valid = await main.ValidAddress(address);
if (!valid)
{
NotifyForm notify = new NotifyForm("Invalid address");
notify.ShowDialog();
notify.Dispose();
buttonSend.Enabled = true;
return;
}
decimal amount = 0;
if (!decimal.TryParse(textBoxAmount.Text, out amount))
{
NotifyForm notify = new NotifyForm("Invalid amount");
notify.ShowDialog();
notify.Dispose();
return;
}
if (amount > unlockedbalance - fee)
{
NotifyForm notify = new NotifyForm("Insufficient balance");
notify.ShowDialog();
notify.Dispose();
return;
}
string content = "{\"method\": \"sendtoaddress\",\"params\": [ \"" + address + "\", " +
amount.ToString() + "]}";
string output = await main.APIPost("", true, content);
JObject APIresp = JObject.Parse(output);
if (APIresp["error"].ToString() != "")
{
main.AddLog("Failed:");
main.AddLog(APIresp.ToString());
JObject error = JObject.Parse(APIresp["error"].ToString());
string ErrorMessage = error["message"].ToString();
NotifyForm notify = new NotifyForm("Error Transaction Failed\n" + ErrorMessage);
notify.ShowDialog();
notify.Dispose();
return;
}
string hash = APIresp["result"].ToString();
string link = main.TXExplorer + hash;
NotifyForm notifySuccess = new NotifyForm("Transaction Sent\nThis transaction could take up to 20 minutes to mine",
"Explorer", link);
notifySuccess.ShowDialog();
notifySuccess.Dispose();
this.Close();
}
} }
}
private async void buttonSend_Click(object sender, EventArgs e)
{
buttonSend.Enabled = false;
var address = textBoxAddress.Text;
if (textBoxAddress.Text.Substring(0, 1) == "@")
{
// HIP-02 not supported yet
var notify = new NotifyForm("HIP-02 not supported yet");
notify.ShowDialog();
notify.Dispose();
buttonSend.Enabled = true;
return;
}
var valid = await main.ValidAddress(address);
if (!valid)
{
var notify = new NotifyForm("Invalid address");
notify.ShowDialog();
notify.Dispose();
buttonSend.Enabled = true;
return;
}
decimal amount = 0;
if (!decimal.TryParse(textBoxAmount.Text, out amount))
{
var notify = new NotifyForm("Invalid amount");
notify.ShowDialog();
notify.Dispose();
return;
}
if (amount > unlockedbalance - fee)
{
var notify = new NotifyForm("Insufficient balance");
notify.ShowDialog();
notify.Dispose();
return;
}
var content = "{\"method\": \"sendtoaddress\",\"params\": [ \"" + address + "\", " +
amount + "]}";
var output = await main.APIPost("", true, content);
var APIresp = JObject.Parse(output);
if (APIresp["error"].ToString() != "")
{
main.AddLog("Failed:");
main.AddLog(APIresp.ToString());
var error = JObject.Parse(APIresp["error"].ToString());
var ErrorMessage = error["message"].ToString();
var notify = new NotifyForm("Error Transaction Failed\n" + ErrorMessage);
notify.ShowDialog();
notify.Dispose();
return;
}
var hash = APIresp["result"].ToString();
var link = main.TXExplorer + hash;
var notifySuccess = new NotifyForm("Transaction Sent\nThis transaction could take up to 20 minutes to mine",
"Explorer", link);
notifySuccess.ShowDialog();
notifySuccess.Dispose();
Close();
}
}

View File

@ -1,96 +1,104 @@
using System.Diagnostics; using System.Diagnostics;
using System.Drawing.Imaging; using System.Drawing.Imaging;
namespace FireWallet;
namespace FireWallet public partial class SplashScreen : Form
{ {
public partial class SplashScreen : Form private bool close;
{ private float opacity;
public SplashScreen(bool timer) private Bitmap splash;
{
InitializeComponent();
close = false;
IsClosed = false;
}
bool close;
float opacity = 0.0f;
private void SplashScreen_FormClosing(object sender, FormClosingEventArgs e)
{
if (!close)
{
e.Cancel = true;
}
}
public bool IsClosed { get; set; }
public void CloseSplash()
{
close = true;
// Fade out public SplashScreen(bool timer)
timerIn.Stop(); {
timerOut.Start(); InitializeComponent();
} close = false;
private void label2_Click(object sender, EventArgs e) IsClosed = false;
}
public bool IsClosed { get; set; }
private void SplashScreen_FormClosing(object sender, FormClosingEventArgs e)
{
if (!close) e.Cancel = true;
}
public void CloseSplash()
{
close = true;
// Fade out
timerIn.Stop();
timerOut.Start();
}
private void label2_Click(object sender, EventArgs e)
{
var psi = new ProcessStartInfo
{ {
ProcessStartInfo psi = new ProcessStartInfo FileName = "https://nathan.woodburn.au",
UseShellExecute = true
};
Process.Start(psi);
}
//new Bitmap(Properties.Resources.FWSplash);
private void SplashScreen_Load(object sender, EventArgs e)
{
splash = pictureBoxNew.Image as Bitmap;
pictureBoxNew.Visible = true;
TransparencyKey = Color.FromArgb(0, 0, 0);
pictureBoxNew.Invalidate();
}
public Image SetImageOpacity(Image image, float opacity)
{
try
{
var bmp = new Bitmap(image.Width, image.Height);
using (var gfx = Graphics.FromImage(bmp))
{ {
FileName = "https://nathan.woodburn.au", var matrix = new ColorMatrix();
UseShellExecute = true matrix.Matrix33 = opacity;
}; var attributes = new ImageAttributes();
Process.Start(psi); attributes.SetColorMatrix(matrix, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
} gfx.DrawImage(image, new Rectangle(0, 0, bmp.Width, bmp.Height), 0, 0, image.Width, image.Height,
Bitmap splash; GraphicsUnit.Pixel, attributes);
//new Bitmap(Properties.Resources.FWSplash);
private void SplashScreen_Load(object sender, EventArgs e)
{
splash = pictureBoxNew.Image as Bitmap;
pictureBoxNew.Visible = true;
this.TransparencyKey = Color.FromArgb(0, 0, 0);
pictureBoxNew.Invalidate();
}
public Image SetImageOpacity(Image image, float opacity)
{
try
{
Bitmap bmp = new Bitmap(image.Width, image.Height);
using (Graphics gfx = Graphics.FromImage(bmp))
{
ColorMatrix matrix = new ColorMatrix();
matrix.Matrix33 = opacity;
ImageAttributes attributes = new ImageAttributes();
attributes.SetColorMatrix(matrix, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
gfx.DrawImage(image, new Rectangle(0, 0, bmp.Width, bmp.Height), 0, 0, image.Width, image.Height, GraphicsUnit.Pixel, attributes);
}
return bmp;
}
catch
{
return null;
} }
return bmp;
} }
private void timerIn_Tick(object sender, EventArgs e) catch
{ {
if (opacity >= 1) return null;
{
timerIn.Stop();
return;
}
opacity += 0.05f;
pictureBoxNew.Image = SetImageOpacity(splash, opacity);
pictureBoxNew.Invalidate();
}
private void timerOut_Tick(object sender, EventArgs e)
{
if (opacity <= 0)
{
timerOut.Stop();
IsClosed = true;
this.Close();
return;
}
opacity -= 0.05f;
pictureBoxNew.Image = SetImageOpacity(splash, opacity);
pictureBoxNew.Invalidate();
} }
} }
}
private void timerIn_Tick(object sender, EventArgs e)
{
if (opacity >= 1)
{
timerIn.Stop();
return;
}
opacity += 0.05f;
pictureBoxNew.Image = SetImageOpacity(splash, opacity);
pictureBoxNew.Invalidate();
}
private void timerOut_Tick(object sender, EventArgs e)
{
if (opacity <= 0)
{
timerOut.Stop();
IsClosed = true;
Close();
return;
}
opacity -= 0.05f;
pictureBoxNew.Image = SetImageOpacity(splash, opacity);
pictureBoxNew.Invalidate();
}
}

744
Installer/Installer.vdproj Normal file
View File

@ -0,0 +1,744 @@
"DeployProject"
{
"VSVersion" = "3:800"
"ProjectType" = "8:{978C614F-708E-4E1A-B201-565925725DBA}"
"IsWebType" = "8:FALSE"
"ProjectName" = "8:Installer"
"LanguageId" = "3:1033"
"CodePage" = "3:1252"
"UILanguageId" = "3:1033"
"SccProjectName" = "8:"
"SccLocalPath" = "8:"
"SccAuxPath" = "8:"
"SccProvider" = "8:"
"Hierarchy"
{
"Entry"
{
"MsmKey" = "8:_AE21837395E3477BAB0C9E460C5F9E1E"
"OwnerKey" = "8:_UNDEFINED"
"MsmSig" = "8:_UNDEFINED"
}
}
"Configurations"
{
"Debug"
{
"DisplayName" = "8:Debug"
"IsDebugOnly" = "11:TRUE"
"IsReleaseOnly" = "11:FALSE"
"OutputFilename" = "8:Debug\\Installer.msi"
"PackageFilesAs" = "3:2"
"PackageFileSize" = "3:-2147483648"
"CabType" = "3:1"
"Compression" = "3:2"
"SignOutput" = "11:FALSE"
"CertificateFile" = "8:"
"PrivateKeyFile" = "8:"
"TimeStampServer" = "8:"
"InstallerBootstrapper" = "3:2"
"BootstrapperCfg:{63ACBE69-63AA-4F98-B2B6-99F9E24495F2}"
{
"Enabled" = "11:TRUE"
"PromptEnabled" = "11:TRUE"
"PrerequisitesLocation" = "2:1"
"Url" = "8:"
"ComponentsUrl" = "8:"
"Items"
{
"{EDC2488A-8267-493A-A98E-7D9C3B36CDF3}:.NETFramework,Version=v4.7.2"
{
"Name" = "8:Microsoft .NET Framework 4.7.2 (x86 and x64)"
"ProductCode" = "8:.NETFramework,Version=v4.7.2"
}
"{EDC2488A-8267-493A-A98E-7D9C3B36CDF3}:Microsoft.NetCore.DesktopRuntime.6.0.x64"
{
"Name" = "8:.NET Desktop Runtime 6.0.18 (x64)"
"ProductCode" = "8:Microsoft.NetCore.DesktopRuntime.6.0.x64"
}
}
}
}
"Release"
{
"DisplayName" = "8:Release"
"IsDebugOnly" = "11:FALSE"
"IsReleaseOnly" = "11:TRUE"
"OutputFilename" = "8:Release\\Installer.msi"
"PackageFilesAs" = "3:2"
"PackageFileSize" = "3:-2147483648"
"CabType" = "3:1"
"Compression" = "3:2"
"SignOutput" = "11:FALSE"
"CertificateFile" = "8:"
"PrivateKeyFile" = "8:"
"TimeStampServer" = "8:"
"InstallerBootstrapper" = "3:2"
"BootstrapperCfg:{63ACBE69-63AA-4F98-B2B6-99F9E24495F2}"
{
"Enabled" = "11:TRUE"
"PromptEnabled" = "11:TRUE"
"PrerequisitesLocation" = "2:1"
"Url" = "8:"
"ComponentsUrl" = "8:"
"Items"
{
"{EDC2488A-8267-493A-A98E-7D9C3B36CDF3}:.NETFramework,Version=v4.7.2"
{
"Name" = "8:Microsoft .NET Framework 4.7.2 (x86 and x64)"
"ProductCode" = "8:.NETFramework,Version=v4.7.2"
}
}
}
}
}
"Deployable"
{
"CustomAction"
{
}
"DefaultFeature"
{
"Name" = "8:DefaultFeature"
"Title" = "8:"
"Description" = "8:"
}
"ExternalPersistence"
{
"LaunchCondition"
{
"{A06ECF26-33A3-4562-8140-9B0E340D4F24}:_5AF7E79AA90B41AAA29786DC3C4C7096"
{
"Name" = "8:.NET Core"
"Message" = "8:[VSDNETCOREMSG]"
"AllowLaterVersions" = "11:FALSE"
"InstallUrl" = "8:https://dotnet.microsoft.com/download/dotnet-core/[NetCoreVerMajorDotMinor]"
"IsNETCore" = "11:TRUE"
"Architecture" = "2:0"
"Runtime" = "2:0"
}
}
}
"File"
{
}
"FileType"
{
}
"Folder"
{
"{1525181F-901A-416C-8A58-119130FE478E}:_C5178F6D7FA7478084860195A2F5CE00"
{
"Name" = "8:#1919"
"AlwaysCreate" = "11:FALSE"
"Condition" = "8:"
"Transitive" = "11:FALSE"
"Property" = "8:ProgramMenuFolder"
"Folders"
{
}
}
"{1525181F-901A-416C-8A58-119130FE478E}:_E1E43FB13F0B48DA98F52FC87B46388F"
{
"Name" = "8:#1916"
"AlwaysCreate" = "11:FALSE"
"Condition" = "8:"
"Transitive" = "11:FALSE"
"Property" = "8:DesktopFolder"
"Folders"
{
}
}
"{3C67513D-01DD-4637-8A68-80971EB9504F}:_F2E4B39C8E3B4447A5FD1EDBBBF6F36B"
{
"DefaultLocation" = "8:[ProgramFilesFolder][ProductName]"
"Name" = "8:#1925"
"AlwaysCreate" = "11:FALSE"
"Condition" = "8:"
"Transitive" = "11:FALSE"
"Property" = "8:TARGETDIR"
"Folders"
{
}
}
}
"LaunchCondition"
{
}
"Locator"
{
}
"MsiBootstrapper"
{
"LangId" = "3:1033"
"RequiresElevation" = "11:FALSE"
}
"Product"
{
"Name" = "8:Microsoft Visual Studio"
"ProductName" = "8:FireWalletLite"
"ProductCode" = "8:{23670E44-E1CD-40B5-881D-40657BD30860}"
"PackageCode" = "8:{2CCCD1E4-40D9-4E58-8D3A-2039BD1CD215}"
"UpgradeCode" = "8:{6966FD44-6B8C-43C0-981A-E36449BF2DA8}"
"AspNetVersion" = "8:"
"RestartWWWService" = "11:FALSE"
"RemovePreviousVersions" = "11:TRUE"
"DetectNewerInstalledVersion" = "11:TRUE"
"InstallAllUsers" = "11:FALSE"
"ProductVersion" = "8:1.0.0"
"Manufacturer" = "8:Nathan.Woodburn/"
"ARPHELPTELEPHONE" = "8:"
"ARPHELPLINK" = "8:"
"Title" = "8:FireWalletLite"
"Subject" = "8:"
"ARPCONTACT" = "8:Nathan.Woodburn/"
"Keywords" = "8:"
"ARPCOMMENTS" = "8:"
"ARPURLINFOABOUT" = "8:"
"ARPPRODUCTICON" = "8:"
"ARPIconIndex" = "3:0"
"SearchPath" = "8:"
"UseSystemSearchPath" = "11:TRUE"
"TargetPlatform" = "3:0"
"PreBuildEvent" = "8:"
"PostBuildEvent" = "8:"
"RunPostBuildEvent" = "3:0"
}
"Registry"
{
"HKLM"
{
"Keys"
{
"{60EA8692-D2D5-43EB-80DC-7906BF13D6EF}:_4CAE988EEDBA48869A26B28C6C1F4BB9"
{
"Name" = "8:Software"
"Condition" = "8:"
"AlwaysCreate" = "11:FALSE"
"DeleteAtUninstall" = "11:FALSE"
"Transitive" = "11:FALSE"
"Keys"
{
"{60EA8692-D2D5-43EB-80DC-7906BF13D6EF}:_65A687F33E58477296CAA0595729195C"
{
"Name" = "8:[Manufacturer]"
"Condition" = "8:"
"AlwaysCreate" = "11:FALSE"
"DeleteAtUninstall" = "11:FALSE"
"Transitive" = "11:FALSE"
"Keys"
{
}
"Values"
{
}
}
}
"Values"
{
}
}
}
}
"HKCU"
{
"Keys"
{
"{60EA8692-D2D5-43EB-80DC-7906BF13D6EF}:_B60CD5397F694FCAB905C352E6CA07AD"
{
"Name" = "8:Software"
"Condition" = "8:"
"AlwaysCreate" = "11:FALSE"
"DeleteAtUninstall" = "11:FALSE"
"Transitive" = "11:FALSE"
"Keys"
{
"{60EA8692-D2D5-43EB-80DC-7906BF13D6EF}:_8E9CCF202A2145E3ABF1FDC18F205A7A"
{
"Name" = "8:[Manufacturer]"
"Condition" = "8:"
"AlwaysCreate" = "11:FALSE"
"DeleteAtUninstall" = "11:FALSE"
"Transitive" = "11:FALSE"
"Keys"
{
}
"Values"
{
}
}
}
"Values"
{
}
}
}
}
"HKCR"
{
"Keys"
{
}
}
"HKU"
{
"Keys"
{
}
}
"HKPU"
{
"Keys"
{
}
}
}
"Sequences"
{
}
"Shortcut"
{
"{970C0BB2-C7D0-45D7-ABFA-7EC378858BC0}:_41DBEDCE7AA04AA6A5749C1CCDA9E389"
{
"Name" = "8:FireWalletLite"
"Arguments" = "8:"
"Description" = "8:"
"ShowCmd" = "3:1"
"IconIndex" = "3:0"
"Transitive" = "11:FALSE"
"Target" = "8:_AE21837395E3477BAB0C9E460C5F9E1E"
"Folder" = "8:_C5178F6D7FA7478084860195A2F5CE00"
"WorkingFolder" = "8:_F2E4B39C8E3B4447A5FD1EDBBBF6F36B"
"Icon" = "8:"
"Feature" = "8:"
}
}
"UserInterface"
{
"{DF760B10-853B-4699-99F2-AFF7185B4A62}:_0CF0510293554C2990129671DA802C05"
{
"Name" = "8:#1902"
"Sequence" = "3:2"
"Attributes" = "3:3"
"Dialogs"
{
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_44CD2A6A59354DF795C3211010308027"
{
"Sequence" = "3:100"
"DisplayName" = "8:Finished"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdAdminFinishedDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
}
}
}
}
"{DF760B10-853B-4699-99F2-AFF7185B4A62}:_0D16658A610C430198D6F91FD4D732D3"
{
"Name" = "8:#1901"
"Sequence" = "3:2"
"Attributes" = "3:2"
"Dialogs"
{
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_C94DF693C5A64464ACBAEB0A1075C332"
{
"Sequence" = "3:100"
"DisplayName" = "8:Progress"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdAdminProgressDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
"ShowProgress"
{
"Name" = "8:ShowProgress"
"DisplayName" = "8:#1009"
"Description" = "8:#1109"
"Type" = "3:5"
"ContextData" = "8:1;True=1;False=0"
"Attributes" = "3:0"
"Setting" = "3:0"
"Value" = "3:1"
"DefaultValue" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
}
}
}
}
"{DF760B10-853B-4699-99F2-AFF7185B4A62}:_558486BDD95E40A5BB80770F8EAA4E67"
{
"Name" = "8:#1901"
"Sequence" = "3:1"
"Attributes" = "3:2"
"Dialogs"
{
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_9853F04696E14F45BF9E2726A1EBE60C"
{
"Sequence" = "3:100"
"DisplayName" = "8:Progress"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdProgressDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
"ShowProgress"
{
"Name" = "8:ShowProgress"
"DisplayName" = "8:#1009"
"Description" = "8:#1109"
"Type" = "3:5"
"ContextData" = "8:1;True=1;False=0"
"Attributes" = "3:0"
"Setting" = "3:0"
"Value" = "3:1"
"DefaultValue" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
}
}
}
}
"{2479F3F5-0309-486D-8047-8187E2CE5BA0}:_5C124147EC93487E8B9C96FBA33DC342"
{
"UseDynamicProperties" = "11:FALSE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdUserInterface.wim"
}
"{DF760B10-853B-4699-99F2-AFF7185B4A62}:_5DAC4010477747D88BC32C17B23E50E3"
{
"Name" = "8:#1900"
"Sequence" = "3:2"
"Attributes" = "3:1"
"Dialogs"
{
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_042F4FCF249B41F784926BA13CFC5792"
{
"Sequence" = "3:200"
"DisplayName" = "8:Installation Folder"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdAdminFolderDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
}
}
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_257C47CAADC54FC38173EC802533721C"
{
"Sequence" = "3:100"
"DisplayName" = "8:Welcome"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdAdminWelcomeDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
"CopyrightWarning"
{
"Name" = "8:CopyrightWarning"
"DisplayName" = "8:#1002"
"Description" = "8:#1102"
"Type" = "3:3"
"ContextData" = "8:"
"Attributes" = "3:0"
"Setting" = "3:1"
"Value" = "8:#1202"
"DefaultValue" = "8:#1202"
"UsePlugInResources" = "11:TRUE"
}
"Welcome"
{
"Name" = "8:Welcome"
"DisplayName" = "8:#1003"
"Description" = "8:#1103"
"Type" = "3:3"
"ContextData" = "8:"
"Attributes" = "3:0"
"Setting" = "3:1"
"Value" = "8:#1203"
"DefaultValue" = "8:#1203"
"UsePlugInResources" = "11:TRUE"
}
}
}
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_F32ECFCDB25A4F72A49C5ABE18380725"
{
"Sequence" = "3:300"
"DisplayName" = "8:Confirm Installation"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdAdminConfirmDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
}
}
}
}
"{2479F3F5-0309-486D-8047-8187E2CE5BA0}:_A40A9D5E6C814841890F5B9F459823E5"
{
"UseDynamicProperties" = "11:FALSE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdBasicDialogs.wim"
}
"{DF760B10-853B-4699-99F2-AFF7185B4A62}:_F6A7465009F84A3C8C006B2BEE5EF5BD"
{
"Name" = "8:#1902"
"Sequence" = "3:1"
"Attributes" = "3:3"
"Dialogs"
{
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_89C1E3A6235947C086DBA8A50608ADDE"
{
"Sequence" = "3:100"
"DisplayName" = "8:Finished"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdFinishedDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
"UpdateText"
{
"Name" = "8:UpdateText"
"DisplayName" = "8:#1058"
"Description" = "8:#1158"
"Type" = "3:15"
"ContextData" = "8:"
"Attributes" = "3:0"
"Setting" = "3:1"
"Value" = "8:#1258"
"DefaultValue" = "8:#1258"
"UsePlugInResources" = "11:TRUE"
}
}
}
}
}
"{DF760B10-853B-4699-99F2-AFF7185B4A62}:_FF3128B8043E4FA9817936D20B319546"
{
"Name" = "8:#1900"
"Sequence" = "3:1"
"Attributes" = "3:1"
"Dialogs"
{
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_1D1CA2281D284F5A88862C7DCAA62F16"
{
"Sequence" = "3:300"
"DisplayName" = "8:Confirm Installation"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdConfirmDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
}
}
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_4F94CBA97362442D91A8822131530A8C"
{
"Sequence" = "3:100"
"DisplayName" = "8:Welcome"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdWelcomeDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
"CopyrightWarning"
{
"Name" = "8:CopyrightWarning"
"DisplayName" = "8:#1002"
"Description" = "8:#1102"
"Type" = "3:3"
"ContextData" = "8:"
"Attributes" = "3:0"
"Setting" = "3:1"
"Value" = "8:#1202"
"DefaultValue" = "8:#1202"
"UsePlugInResources" = "11:TRUE"
}
"Welcome"
{
"Name" = "8:Welcome"
"DisplayName" = "8:#1003"
"Description" = "8:#1103"
"Type" = "3:3"
"ContextData" = "8:"
"Attributes" = "3:0"
"Setting" = "3:1"
"Value" = "8:#1203"
"DefaultValue" = "8:#1203"
"UsePlugInResources" = "11:TRUE"
}
}
}
"{688940B3-5CA9-4162-8DEE-2993FA9D8CBC}:_CA81350D69B4450C846CB4A31EE35251"
{
"Sequence" = "3:200"
"DisplayName" = "8:Installation Folder"
"UseDynamicProperties" = "11:TRUE"
"IsDependency" = "11:FALSE"
"SourcePath" = "8:<VsdDialogDir>\\VsdFolderDlg.wid"
"Properties"
{
"BannerBitmap"
{
"Name" = "8:BannerBitmap"
"DisplayName" = "8:#1001"
"Description" = "8:#1101"
"Type" = "3:8"
"ContextData" = "8:Bitmap"
"Attributes" = "3:4"
"Setting" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
"InstallAllUsersVisible"
{
"Name" = "8:InstallAllUsersVisible"
"DisplayName" = "8:#1059"
"Description" = "8:#1159"
"Type" = "3:5"
"ContextData" = "8:1;True=1;False=0"
"Attributes" = "3:0"
"Setting" = "3:0"
"Value" = "3:1"
"DefaultValue" = "3:1"
"UsePlugInResources" = "11:TRUE"
}
}
}
}
}
}
"MergeModule"
{
}
"ProjectOutput"
{
"{5259A561-127C-4D43-A0A1-72F10C7B3BF8}:_AE21837395E3477BAB0C9E460C5F9E1E"
{
"SourcePath" = "8:..\\FireWalletLite\\obj\\Debug\\net6.0-windows\\apphost.exe"
"TargetName" = "8:"
"Tag" = "8:"
"Folder" = "8:_F2E4B39C8E3B4447A5FD1EDBBBF6F36B"
"Condition" = "8:"
"Transitive" = "11:FALSE"
"Vital" = "11:TRUE"
"ReadOnly" = "11:FALSE"
"Hidden" = "11:FALSE"
"System" = "11:FALSE"
"Permanent" = "11:FALSE"
"SharedLegacy" = "11:FALSE"
"PackageAs" = "3:1"
"Register" = "3:1"
"Exclude" = "11:FALSE"
"IsDependency" = "11:FALSE"
"IsolateTo" = "8:"
"ProjectOutputGroupRegister" = "3:1"
"OutputConfiguration" = "8:"
"OutputGroupCanonicalName" = "8:PublishItems"
"OutputProjectGuid" = "8:{A375882A-CB5E-4268-A6CC-106B270EE200}"
"ShowKeyOutput" = "11:TRUE"
"ExcludeFilters"
{
}
}
}
}
}

View File

@ -1,6 +1,9 @@
# FireWalletLite # FireWalletLite
A lite wallet for Handshake. A lite wallet for Handshake.
This is aimed to be mainly used for holding HNS and domains without sending anything. This is aimed to be mainly used for holding HNS and domains without sending anything.
For example if you want to gift a domain to someone, you can have them use this wallet to store the wallet.
You will still need to renew the domains at least every 2 years.
## Features ## Features
First run flow: First run flow:
@ -28,4 +31,11 @@ This wallet does not (and will never) support
- DNS management - DNS management
If you want to use a wallet with more features, please use [Fire Wallet](https://firewallet.au) or [Bob Wallet](https://bobwallet.io) instead. If you want to use a wallet with more features, please use [Fire Wallet](https://firewallet.au) or [Bob Wallet](https://bobwallet.io) instead.
## Install
FireWalletLite is available for Windows only.
You can download the latest prebuilt release from [here](https://git.woodburn.au/nathanwoodburn/FireWalletLite/releases).
You should download the `FireWalletLite.zip` file and extract it to a folder then run the `setup.exe` file as this file will install the .net runtime if it is not already installed.
**You can also build it yourself by cloning this repo and building it in Visual Studio.**