mirror of
https://github.com/sparrowwallet/sparrow.git
synced 2024-12-25 13:16:44 +00:00
improve input and output labels on transaction tree and detail panels
This commit is contained in:
parent
540424a2e3
commit
57dba5d6ae
14 changed files with 367 additions and 266 deletions
2
drongo
2
drongo
|
@ -1 +1 @@
|
||||||
Subproject commit 78944a7114f5e22d0622dd07ca426e04acdce5b7
|
Subproject commit 42f279e5e7cfdcf0de80f60f65857d26db8580ad
|
|
@ -14,6 +14,7 @@ import com.sparrowwallet.sparrow.event.ExcludeUtxoEvent;
|
||||||
import com.sparrowwallet.sparrow.event.ReplaceChangeAddressEvent;
|
import com.sparrowwallet.sparrow.event.ReplaceChangeAddressEvent;
|
||||||
import com.sparrowwallet.sparrow.event.SorobanInitiatedEvent;
|
import com.sparrowwallet.sparrow.event.SorobanInitiatedEvent;
|
||||||
import com.sparrowwallet.sparrow.glyphfont.FontAwesome5;
|
import com.sparrowwallet.sparrow.glyphfont.FontAwesome5;
|
||||||
|
import com.sparrowwallet.sparrow.glyphfont.GlyphUtils;
|
||||||
import com.sparrowwallet.sparrow.io.Config;
|
import com.sparrowwallet.sparrow.io.Config;
|
||||||
import com.sparrowwallet.sparrow.soroban.SorobanServices;
|
import com.sparrowwallet.sparrow.soroban.SorobanServices;
|
||||||
import com.sparrowwallet.sparrow.wallet.OptimizationStrategy;
|
import com.sparrowwallet.sparrow.wallet.OptimizationStrategy;
|
||||||
|
@ -44,7 +45,6 @@ import javafx.stage.Modality;
|
||||||
import javafx.stage.Stage;
|
import javafx.stage.Stage;
|
||||||
import javafx.stage.StageStyle;
|
import javafx.stage.StageStyle;
|
||||||
import javafx.util.Duration;
|
import javafx.util.Duration;
|
||||||
import org.controlsfx.glyphfont.FontAwesome;
|
|
||||||
import org.controlsfx.glyphfont.Glyph;
|
import org.controlsfx.glyphfont.Glyph;
|
||||||
import org.controlsfx.tools.Platform;
|
import org.controlsfx.tools.Platform;
|
||||||
|
|
||||||
|
@ -56,6 +56,8 @@ import java.util.*;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
import static com.sparrowwallet.sparrow.glyphfont.GlyphUtils.*;
|
||||||
|
|
||||||
public class TransactionDiagram extends GridPane {
|
public class TransactionDiagram extends GridPane {
|
||||||
private static final int MAX_UTXOS = 8;
|
private static final int MAX_UTXOS = 8;
|
||||||
private static final int REDUCED_MAX_UTXOS = MAX_UTXOS - 2;
|
private static final int REDUCED_MAX_UTXOS = MAX_UTXOS - 2;
|
||||||
|
@ -686,19 +688,18 @@ public class TransactionDiagram extends GridPane {
|
||||||
|
|
||||||
List<OutputNode> outputNodes = new ArrayList<>();
|
List<OutputNode> outputNodes = new ArrayList<>();
|
||||||
for(Payment payment : displayedPayments) {
|
for(Payment payment : displayedPayments) {
|
||||||
Glyph outputGlyph = getOutputGlyph(payment);
|
Glyph outputGlyph = GlyphUtils.getOutputGlyph(walletTx, payment);
|
||||||
boolean labelledPayment = outputGlyph.getStyleClass().stream().anyMatch(style -> List.of("premix-icon", "badbank-icon", "whirlpoolfee-icon").contains(style)) || payment instanceof AdditionalPayment;
|
boolean labelledPayment = outputGlyph.getStyleClass().stream().anyMatch(style -> List.of("premix-icon", "badbank-icon", "whirlpoolfee-icon").contains(style)) || payment instanceof AdditionalPayment;
|
||||||
payment.setLabel(getOutputLabel(payment));
|
|
||||||
Label recipientLabel = new Label(payment.getLabel() == null || payment.getType() == Payment.Type.FAKE_MIX || payment.getType() == Payment.Type.MIX ? payment.getAddress().toString().substring(0, 8) + "..." : payment.getLabel(), outputGlyph);
|
Label recipientLabel = new Label(payment.getLabel() == null || payment.getType() == Payment.Type.FAKE_MIX || payment.getType() == Payment.Type.MIX ? payment.getAddress().toString().substring(0, 8) + "..." : payment.getLabel(), outputGlyph);
|
||||||
recipientLabel.getStyleClass().add("output-label");
|
recipientLabel.getStyleClass().add("output-label");
|
||||||
recipientLabel.getStyleClass().add(labelledPayment ? "payment-label" : "recipient-label");
|
recipientLabel.getStyleClass().add(labelledPayment ? "payment-label" : "recipient-label");
|
||||||
Wallet toWallet = getToWallet(payment);
|
Wallet toWallet = walletTx.getToWallet(AppServices.get().getOpenWallets().keySet(), payment);
|
||||||
WalletNode toNode = walletTx.getWallet() != null && !walletTx.getWallet().isBip47() ? walletTx.getAddressNodeMap().get(payment.getAddress()) : null;
|
WalletNode toNode = walletTx.getWallet() != null && !walletTx.getWallet().isBip47() ? walletTx.getAddressNodeMap().get(payment.getAddress()) : null;
|
||||||
Wallet toBip47Wallet = getBip47SendWallet(payment);
|
Wallet toBip47Wallet = getBip47SendWallet(payment);
|
||||||
Tooltip recipientTooltip = new Tooltip((toWallet == null ? (toNode != null ? "Consolidate " : "Pay ") : "Receive ")
|
Tooltip recipientTooltip = new Tooltip((toWallet == null ? (toNode != null ? "Consolidate " : "Pay ") : "Receive ")
|
||||||
+ getSatsValue(payment.getAmount()) + " sats to "
|
+ getSatsValue(payment.getAmount()) + " sats to "
|
||||||
+ (payment instanceof AdditionalPayment ? (isExpanded() ? "\n" : "(click to expand)\n") + payment : (toWallet == null ? (payment.getLabel() == null ? (toNode != null ? toNode : (toBip47Wallet == null ? "external address" : toBip47Wallet.getDisplayName())) : payment.getLabel()) : toWallet.getFullDisplayName()) + "\n" + payment.getAddress().toString())
|
+ (payment instanceof AdditionalPayment ? (isExpanded() ? "\n" : "(click to expand)\n") + payment : (toWallet == null ? (payment.getLabel() == null ? (toNode != null ? toNode : (toBip47Wallet == null ? "external address" : toBip47Wallet.getDisplayName())) : payment.getLabel()) : toWallet.getFullDisplayName()) + "\n" + payment.getAddress().toString())
|
||||||
+ (isDuplicateAddress(payment) ? " (Duplicate)" : ""));
|
+ (walletTx.isDuplicateAddress(payment) ? " (Duplicate)" : ""));
|
||||||
recipientTooltip.getStyleClass().add("recipient-label");
|
recipientTooltip.getStyleClass().add("recipient-label");
|
||||||
recipientTooltip.setShowDelay(new Duration(TOOLTIP_SHOW_DELAY));
|
recipientTooltip.setShowDelay(new Duration(TOOLTIP_SHOW_DELAY));
|
||||||
recipientTooltip.setShowDuration(Duration.INDEFINITE);
|
recipientTooltip.setShowDuration(Duration.INDEFINITE);
|
||||||
|
@ -928,42 +929,12 @@ public class TransactionDiagram extends GridPane {
|
||||||
return spacer;
|
return spacer;
|
||||||
}
|
}
|
||||||
|
|
||||||
private String getOutputLabel(Payment payment) {
|
|
||||||
if(payment.getLabel() != null) {
|
|
||||||
return payment.getLabel();
|
|
||||||
}
|
|
||||||
|
|
||||||
if(payment.getType() == Payment.Type.WHIRLPOOL_FEE) {
|
|
||||||
return "Whirlpool fee";
|
|
||||||
} else if(walletTx.isPremixSend(payment)) {
|
|
||||||
int premixIndex = getOutputIndex(payment.getAddress(), payment.getAmount(), Collections.emptySet()) - 1;
|
|
||||||
return "Premix #" + premixIndex;
|
|
||||||
} else if(walletTx.isBadbankSend(payment)) {
|
|
||||||
return "Badbank change";
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private int getOutputIndex(Address address, long amount, Collection<Integer> seenIndexes) {
|
private int getOutputIndex(Address address, long amount, Collection<Integer> seenIndexes) {
|
||||||
List<TransactionOutput> addressOutputs = walletTx.getTransaction().getOutputs().stream().filter(txOutput -> txOutput.getScript().getToAddress() != null).collect(Collectors.toList());
|
List<TransactionOutput> addressOutputs = walletTx.getTransaction().getOutputs().stream().filter(txOutput -> txOutput.getScript().getToAddress() != null).collect(Collectors.toList());
|
||||||
TransactionOutput output = addressOutputs.stream().filter(txOutput -> address.equals(txOutput.getScript().getToAddress()) && txOutput.getValue() == amount && !seenIndexes.contains(txOutput.getIndex())).findFirst().orElseThrow();
|
TransactionOutput output = addressOutputs.stream().filter(txOutput -> address.equals(txOutput.getScript().getToAddress()) && txOutput.getValue() == amount && !seenIndexes.contains(txOutput.getIndex())).findFirst().orElseThrow();
|
||||||
return addressOutputs.indexOf(output);
|
return addressOutputs.indexOf(output);
|
||||||
}
|
}
|
||||||
|
|
||||||
Wallet getToWallet(Payment payment) {
|
|
||||||
for(Wallet openWallet : AppServices.get().getOpenWallets().keySet()) {
|
|
||||||
if(openWallet != walletTx.getWallet() && openWallet.isValid()) {
|
|
||||||
WalletNode addressNode = openWallet.getWalletAddresses().get(payment.getAddress());
|
|
||||||
if(addressNode != null) {
|
|
||||||
return addressNode.getWallet();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Wallet getBip47SendWallet(Payment payment) {
|
private Wallet getBip47SendWallet(Payment payment) {
|
||||||
if(walletTx.getWallet() != null) {
|
if(walletTx.getWallet() != null) {
|
||||||
for(Wallet childWallet : walletTx.getWallet().getChildWallets()) {
|
for(Wallet childWallet : walletTx.getWallet().getChildWallets()) {
|
||||||
|
@ -981,164 +952,6 @@ public class TransactionDiagram extends GridPane {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Glyph getOutputGlyph(Payment payment) {
|
|
||||||
if(payment.getType().equals(Payment.Type.MIX)) {
|
|
||||||
return getMixGlyph();
|
|
||||||
} else if(payment.getType().equals(Payment.Type.FAKE_MIX)) {
|
|
||||||
return getFakeMixGlyph();
|
|
||||||
} else if(walletTx.isConsolidationSend(payment)) {
|
|
||||||
return getConsolidationGlyph();
|
|
||||||
} else if(walletTx.isPremixSend(payment)) {
|
|
||||||
return getPremixGlyph();
|
|
||||||
} else if(walletTx.isBadbankSend(payment)) {
|
|
||||||
return getBadbankGlyph();
|
|
||||||
} else if(payment.getType().equals(Payment.Type.WHIRLPOOL_FEE)) {
|
|
||||||
return getWhirlpoolFeeGlyph();
|
|
||||||
} else if(payment instanceof AdditionalPayment) {
|
|
||||||
return ((AdditionalPayment)payment).getOutputGlyph(this);
|
|
||||||
} else if(getToWallet(payment) != null) {
|
|
||||||
return getDepositGlyph();
|
|
||||||
} else if(isDuplicateAddress(payment)) {
|
|
||||||
return getPaymentWarningGlyph();
|
|
||||||
}
|
|
||||||
|
|
||||||
return getPaymentGlyph();
|
|
||||||
}
|
|
||||||
|
|
||||||
private boolean isDuplicateAddress(Payment payment) {
|
|
||||||
return walletTx.getPayments().stream().filter(p -> payment != p).anyMatch(p -> payment.getAddress() != null && payment.getAddress().equals(p.getAddress()));
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getExcludeGlyph() {
|
|
||||||
Glyph excludeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.TIMES_CIRCLE);
|
|
||||||
excludeGlyph.getStyleClass().add("exclude-utxo");
|
|
||||||
excludeGlyph.setFontSize(12);
|
|
||||||
return excludeGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getPaymentGlyph() {
|
|
||||||
Glyph paymentGlyph = new Glyph("FontAwesome", FontAwesome.Glyph.SEND);
|
|
||||||
paymentGlyph.getStyleClass().add("payment-icon");
|
|
||||||
paymentGlyph.setFontSize(12);
|
|
||||||
return paymentGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getPaymentWarningGlyph() {
|
|
||||||
Glyph paymentWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.EXCLAMATION_TRIANGLE);
|
|
||||||
paymentWarningGlyph.getStyleClass().add("payment-warning-icon");
|
|
||||||
paymentWarningGlyph.setFontSize(12);
|
|
||||||
return paymentWarningGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getConsolidationGlyph() {
|
|
||||||
Glyph consolidationGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.REPLY_ALL);
|
|
||||||
consolidationGlyph.getStyleClass().add("consolidation-icon");
|
|
||||||
consolidationGlyph.setFontSize(12);
|
|
||||||
return consolidationGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getDepositGlyph() {
|
|
||||||
Glyph depositGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.ARROW_DOWN);
|
|
||||||
depositGlyph.getStyleClass().add("deposit-icon");
|
|
||||||
depositGlyph.setFontSize(12);
|
|
||||||
return depositGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getPremixGlyph() {
|
|
||||||
Glyph premixGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.RANDOM);
|
|
||||||
premixGlyph.getStyleClass().add("premix-icon");
|
|
||||||
premixGlyph.setFontSize(12);
|
|
||||||
return premixGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getBadbankGlyph() {
|
|
||||||
Glyph badbankGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.BIOHAZARD);
|
|
||||||
badbankGlyph.getStyleClass().add("badbank-icon");
|
|
||||||
badbankGlyph.setFontSize(12);
|
|
||||||
return badbankGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getWhirlpoolFeeGlyph() {
|
|
||||||
Glyph whirlpoolFeeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.HAND_HOLDING_WATER);
|
|
||||||
whirlpoolFeeGlyph.getStyleClass().add("whirlpoolfee-icon");
|
|
||||||
whirlpoolFeeGlyph.setFontSize(12);
|
|
||||||
return whirlpoolFeeGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getFakeMixGlyph() {
|
|
||||||
Glyph fakeMixGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.THEATER_MASKS);
|
|
||||||
fakeMixGlyph.getStyleClass().add("fakemix-icon");
|
|
||||||
fakeMixGlyph.setFontSize(12);
|
|
||||||
return fakeMixGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getTxoGlyph() {
|
|
||||||
return getChangeGlyph();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getMixGlyph() {
|
|
||||||
Glyph payjoinGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.RANDOM);
|
|
||||||
payjoinGlyph.getStyleClass().add("mix-icon");
|
|
||||||
payjoinGlyph.setFontSize(12);
|
|
||||||
return payjoinGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getChangeGlyph() {
|
|
||||||
Glyph changeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.COINS);
|
|
||||||
changeGlyph.getStyleClass().add("change-icon");
|
|
||||||
changeGlyph.setFontSize(12);
|
|
||||||
return changeGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getChangeWarningGlyph() {
|
|
||||||
Glyph changeWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.EXCLAMATION_TRIANGLE);
|
|
||||||
changeWarningGlyph.getStyleClass().add("change-warning-icon");
|
|
||||||
changeWarningGlyph.setFontSize(12);
|
|
||||||
return changeWarningGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Glyph getChangeReplaceGlyph() {
|
|
||||||
Glyph changeReplaceGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.ARROW_DOWN);
|
|
||||||
changeReplaceGlyph.getStyleClass().add("change-replace-icon");
|
|
||||||
changeReplaceGlyph.setFontSize(12);
|
|
||||||
return changeReplaceGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Glyph getFeeGlyph() {
|
|
||||||
Glyph feeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.HAND_HOLDING);
|
|
||||||
feeGlyph.getStyleClass().add("fee-icon");
|
|
||||||
feeGlyph.setFontSize(12);
|
|
||||||
return feeGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Glyph getWarningGlyph() {
|
|
||||||
Glyph feeWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.EXCLAMATION_CIRCLE);
|
|
||||||
feeWarningGlyph.getStyleClass().add("fee-warning-icon");
|
|
||||||
feeWarningGlyph.setFontSize(12);
|
|
||||||
return feeWarningGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Glyph getQuestionGlyph() {
|
|
||||||
Glyph feeWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.QUESTION_CIRCLE);
|
|
||||||
feeWarningGlyph.getStyleClass().add("question-icon");
|
|
||||||
feeWarningGlyph.setFontSize(12);
|
|
||||||
return feeWarningGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Glyph getLockGlyph() {
|
|
||||||
Glyph lockGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.LOCK);
|
|
||||||
lockGlyph.getStyleClass().add("lock-icon");
|
|
||||||
lockGlyph.setFontSize(12);
|
|
||||||
return lockGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Glyph getUserGlyph() {
|
|
||||||
Glyph userGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.USER);
|
|
||||||
userGlyph.getStyleClass().add("user-icon");
|
|
||||||
userGlyph.setFontSize(12);
|
|
||||||
return userGlyph;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Glyph getUserAddGlyph() {
|
private Glyph getUserAddGlyph() {
|
||||||
Glyph userAddGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.USER_PLUS);
|
Glyph userAddGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.USER_PLUS);
|
||||||
userAddGlyph.getStyleClass().add("useradd-icon");
|
userAddGlyph.getStyleClass().add("useradd-icon");
|
||||||
|
@ -1295,7 +1108,7 @@ public class TransactionDiagram extends GridPane {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static class AdditionalPayment extends Payment {
|
public static class AdditionalPayment extends Payment {
|
||||||
private final List<Payment> additionalPayments;
|
private final List<Payment> additionalPayments;
|
||||||
|
|
||||||
public AdditionalPayment(List<Payment> additionalPayments) {
|
public AdditionalPayment(List<Payment> additionalPayments) {
|
||||||
|
@ -1303,10 +1116,10 @@ public class TransactionDiagram extends GridPane {
|
||||||
this.additionalPayments = additionalPayments;
|
this.additionalPayments = additionalPayments;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Glyph getOutputGlyph(TransactionDiagram transactionDiagram) {
|
public Glyph getOutputGlyph(WalletTransaction walletTx) {
|
||||||
Glyph glyph = null;
|
Glyph glyph = null;
|
||||||
for(Payment payment : additionalPayments) {
|
for(Payment payment : additionalPayments) {
|
||||||
Glyph paymentGlyph = transactionDiagram.getOutputGlyph(payment);
|
Glyph paymentGlyph = GlyphUtils.getOutputGlyph(walletTx, payment);
|
||||||
if(glyph != null && !paymentGlyph.getStyleClass().equals(glyph.getStyleClass())) {
|
if(glyph != null && !paymentGlyph.getStyleClass().equals(glyph.getStyleClass())) {
|
||||||
return getPaymentGlyph();
|
return getPaymentGlyph();
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,7 +1,9 @@
|
||||||
package com.sparrowwallet.sparrow.control;
|
package com.sparrowwallet.sparrow.control;
|
||||||
|
|
||||||
import com.sparrowwallet.drongo.wallet.*;
|
import com.sparrowwallet.drongo.wallet.*;
|
||||||
|
import com.sparrowwallet.sparrow.AppServices;
|
||||||
import com.sparrowwallet.sparrow.glyphfont.FontAwesome5;
|
import com.sparrowwallet.sparrow.glyphfont.FontAwesome5;
|
||||||
|
import com.sparrowwallet.sparrow.glyphfont.GlyphUtils;
|
||||||
import javafx.beans.property.IntegerProperty;
|
import javafx.beans.property.IntegerProperty;
|
||||||
import javafx.beans.property.SimpleIntegerProperty;
|
import javafx.beans.property.SimpleIntegerProperty;
|
||||||
import javafx.geometry.Pos;
|
import javafx.geometry.Pos;
|
||||||
|
@ -81,13 +83,13 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
List<Payment> badbankOutputs = walletTx.getPayments().stream().filter(walletTx::isBadbankSend).collect(Collectors.toList());
|
List<Payment> badbankOutputs = walletTx.getPayments().stream().filter(walletTx::isBadbankSend).collect(Collectors.toList());
|
||||||
List<OutputLabel> badbankOutputLabels = badbankOutputs.stream().map(payment -> getBadbankOutputLabel(transactionDiagram, payment)).collect(Collectors.toList());
|
List<OutputLabel> badbankOutputLabels = badbankOutputs.stream().map(payment -> getBadbankOutputLabel(transactionDiagram, payment)).collect(Collectors.toList());
|
||||||
outputLabels.addAll(badbankOutputLabels);
|
outputLabels.addAll(badbankOutputLabels);
|
||||||
} else if(walletTx.getPayments().size() >= 5 && walletTx.getPayments().stream().mapToLong(Payment::getAmount).distinct().count() <= 1
|
} else if(walletTx.getPayments().size() >= 5 && walletTx.getPayments().stream().mapToLong(Payment::getAmount).distinct().count() <= 1 && walletTx.getWallet() != null
|
||||||
&& walletTx.getWallet().getStandardAccountType() == StandardAccount.WHIRLPOOL_PREMIX && walletTx.getPayments().stream().anyMatch(walletTx::isPostmixSend)) {
|
&& walletTx.getWallet().getStandardAccountType() == StandardAccount.WHIRLPOOL_PREMIX && walletTx.getPayments().stream().anyMatch(walletTx::isPostmixSend)) {
|
||||||
OutputLabel mixOutputLabel = getMixOutputLabel(transactionDiagram, walletTx.getPayments());
|
OutputLabel mixOutputLabel = getMixOutputLabel(transactionDiagram, walletTx.getPayments());
|
||||||
if(mixOutputLabel != null) {
|
if(mixOutputLabel != null) {
|
||||||
outputLabels.add(mixOutputLabel);
|
outputLabels.add(mixOutputLabel);
|
||||||
}
|
}
|
||||||
} else if(walletTx.getPayments().size() >= 5 && walletTx.getPayments().stream().mapToLong(Payment::getAmount).distinct().count() <= 1
|
} else if(walletTx.getPayments().size() >= 5 && walletTx.getPayments().stream().mapToLong(Payment::getAmount).distinct().count() <= 1 && walletTx.getWallet() != null
|
||||||
&& walletTx.getWallet().getStandardAccountType() == StandardAccount.WHIRLPOOL_POSTMIX && walletTx.getPayments().stream().anyMatch(walletTx::isConsolidationSend)) {
|
&& walletTx.getWallet().getStandardAccountType() == StandardAccount.WHIRLPOOL_POSTMIX && walletTx.getPayments().stream().anyMatch(walletTx::isConsolidationSend)) {
|
||||||
OutputLabel remixOutputLabel = getRemixOutputLabel(transactionDiagram, walletTx.getPayments());
|
OutputLabel remixOutputLabel = getRemixOutputLabel(transactionDiagram, walletTx.getPayments());
|
||||||
if(remixOutputLabel != null) {
|
if(remixOutputLabel != null) {
|
||||||
|
@ -142,7 +144,7 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
|
|
||||||
Payment premixOutput = premixOutputs.get(0);
|
Payment premixOutput = premixOutputs.get(0);
|
||||||
long total = premixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
long total = premixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
||||||
Glyph glyph = transactionDiagram.getOutputGlyph(premixOutput);
|
Glyph glyph = GlyphUtils.getOutputGlyph(transactionDiagram.getWalletTransaction(), premixOutput);
|
||||||
String text;
|
String text;
|
||||||
if(premixOutputs.size() == 1) {
|
if(premixOutputs.size() == 1) {
|
||||||
text = "Premix transaction with 1 output of " + transactionDiagram.getSatsValue(premixOutput.getAmount()) + " sats";
|
text = "Premix transaction with 1 output of " + transactionDiagram.getSatsValue(premixOutput.getAmount()) + " sats";
|
||||||
|
@ -155,7 +157,7 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
}
|
}
|
||||||
|
|
||||||
private OutputLabel getBadbankOutputLabel(TransactionDiagram transactionDiagram, Payment payment) {
|
private OutputLabel getBadbankOutputLabel(TransactionDiagram transactionDiagram, Payment payment) {
|
||||||
Glyph glyph = transactionDiagram.getOutputGlyph(payment);
|
Glyph glyph = GlyphUtils.getOutputGlyph(transactionDiagram.getWalletTransaction(), payment);
|
||||||
String text = "Badbank change of " + transactionDiagram.getSatsValue(payment.getAmount()) + " sats to " + payment.getAddress().toString();
|
String text = "Badbank change of " + transactionDiagram.getSatsValue(payment.getAmount()) + " sats to " + payment.getAddress().toString();
|
||||||
|
|
||||||
return getOutputLabel(glyph, text);
|
return getOutputLabel(glyph, text);
|
||||||
|
@ -164,7 +166,7 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
private OutputLabel getWhirlpoolFeeOutputLabel(TransactionDiagram transactionDiagram, Payment whirlpoolFee, List<Payment> premixOutputs) {
|
private OutputLabel getWhirlpoolFeeOutputLabel(TransactionDiagram transactionDiagram, Payment whirlpoolFee, List<Payment> premixOutputs) {
|
||||||
long total = premixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
long total = premixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
||||||
double feePercentage = (double)whirlpoolFee.getAmount() / (total - whirlpoolFee.getAmount());
|
double feePercentage = (double)whirlpoolFee.getAmount() / (total - whirlpoolFee.getAmount());
|
||||||
Glyph glyph = transactionDiagram.getOutputGlyph(whirlpoolFee);
|
Glyph glyph = GlyphUtils.getOutputGlyph(transactionDiagram.getWalletTransaction(), whirlpoolFee);
|
||||||
String text = "Whirlpool fee of " + transactionDiagram.getSatsValue(whirlpoolFee.getAmount()) + " sats (" + String.format("%.2f", feePercentage * 100.0) + "% of total premix value)";
|
String text = "Whirlpool fee of " + transactionDiagram.getSatsValue(whirlpoolFee.getAmount()) + " sats (" + String.format("%.2f", feePercentage * 100.0) + "% of total premix value)";
|
||||||
|
|
||||||
return getOutputLabel(glyph, text);
|
return getOutputLabel(glyph, text);
|
||||||
|
@ -177,7 +179,7 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
|
|
||||||
Payment remixOutput = mixOutputs.get(0);
|
Payment remixOutput = mixOutputs.get(0);
|
||||||
long total = mixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
long total = mixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
||||||
Glyph glyph = TransactionDiagram.getPremixGlyph();
|
Glyph glyph = GlyphUtils.getPremixGlyph();
|
||||||
String text = "Mix transaction with " + mixOutputs.size() + " outputs of " + transactionDiagram.getSatsValue(remixOutput.getAmount()) + " sats each ("
|
String text = "Mix transaction with " + mixOutputs.size() + " outputs of " + transactionDiagram.getSatsValue(remixOutput.getAmount()) + " sats each ("
|
||||||
+ transactionDiagram.getSatsValue(total) + " sats)";
|
+ transactionDiagram.getSatsValue(total) + " sats)";
|
||||||
|
|
||||||
|
@ -191,7 +193,7 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
|
|
||||||
Payment remixOutput = remixOutputs.get(0);
|
Payment remixOutput = remixOutputs.get(0);
|
||||||
long total = remixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
long total = remixOutputs.stream().mapToLong(Payment::getAmount).sum();
|
||||||
Glyph glyph = TransactionDiagram.getPremixGlyph();
|
Glyph glyph = GlyphUtils.getPremixGlyph();
|
||||||
String text = "Remix transaction with " + remixOutputs.size() + " outputs of " + transactionDiagram.getSatsValue(remixOutput.getAmount()) + " sats each ("
|
String text = "Remix transaction with " + remixOutputs.size() + " outputs of " + transactionDiagram.getSatsValue(remixOutput.getAmount()) + " sats each ("
|
||||||
+ transactionDiagram.getSatsValue(total) + " sats)";
|
+ transactionDiagram.getSatsValue(total) + " sats)";
|
||||||
|
|
||||||
|
@ -200,10 +202,10 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
|
|
||||||
private OutputLabel getOutputLabel(TransactionDiagram transactionDiagram, Payment payment) {
|
private OutputLabel getOutputLabel(TransactionDiagram transactionDiagram, Payment payment) {
|
||||||
WalletTransaction walletTx = transactionDiagram.getWalletTransaction();
|
WalletTransaction walletTx = transactionDiagram.getWalletTransaction();
|
||||||
Wallet toWallet = transactionDiagram.getToWallet(payment);
|
Wallet toWallet = walletTx.getToWallet(AppServices.get().getOpenWallets().keySet(), payment);
|
||||||
WalletNode toNode = walletTx.getWallet() != null && !walletTx.getWallet().isBip47() ? walletTx.getAddressNodeMap().get(payment.getAddress()) : null;
|
WalletNode toNode = walletTx.getWallet() != null && !walletTx.getWallet().isBip47() ? walletTx.getAddressNodeMap().get(payment.getAddress()) : null;
|
||||||
|
|
||||||
Glyph glyph = transactionDiagram.getOutputGlyph(payment);
|
Glyph glyph = GlyphUtils.getOutputGlyph(transactionDiagram.getWalletTransaction(), payment);
|
||||||
String text = (toWallet == null ? (toNode != null ? "Consolidate " : "Pay ") : "Receive ") + transactionDiagram.getSatsValue(payment.getAmount()) + " sats to " + payment.getAddress().toString();
|
String text = (toWallet == null ? (toNode != null ? "Consolidate " : "Pay ") : "Receive ") + transactionDiagram.getSatsValue(payment.getAmount()) + " sats to " + payment.getAddress().toString();
|
||||||
|
|
||||||
return getOutputLabel(glyph, text);
|
return getOutputLabel(glyph, text);
|
||||||
|
@ -212,7 +214,7 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
private OutputLabel getOutputLabel(TransactionDiagram transactionDiagram, Map.Entry<WalletNode, Long> changeEntry) {
|
private OutputLabel getOutputLabel(TransactionDiagram transactionDiagram, Map.Entry<WalletNode, Long> changeEntry) {
|
||||||
WalletTransaction walletTx = transactionDiagram.getWalletTransaction();
|
WalletTransaction walletTx = transactionDiagram.getWalletTransaction();
|
||||||
|
|
||||||
Glyph glyph = TransactionDiagram.getChangeGlyph();
|
Glyph glyph = GlyphUtils.getChangeGlyph();
|
||||||
String text = "Change of " + transactionDiagram.getSatsValue(changeEntry.getValue()) + " sats to " + walletTx.getChangeAddress(changeEntry.getKey()).toString();
|
String text = "Change of " + transactionDiagram.getSatsValue(changeEntry.getValue()) + " sats to " + walletTx.getChangeAddress(changeEntry.getKey()).toString();
|
||||||
|
|
||||||
return getOutputLabel(glyph, text);
|
return getOutputLabel(glyph, text);
|
||||||
|
@ -224,7 +226,7 @@ public class TransactionDiagramLabel extends HBox {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
Glyph glyph = transactionDiagram.getFeeGlyph();
|
Glyph glyph = GlyphUtils.getFeeGlyph();
|
||||||
String text = "Fee of " + transactionDiagram.getSatsValue(walletTx.getFee()) + " sats (" + String.format("%.2f", walletTx.getFeePercentage() * 100.0) + "%)";
|
String text = "Fee of " + transactionDiagram.getSatsValue(walletTx.getFee()) + " sats (" + String.format("%.2f", walletTx.getFeePercentage() * 100.0) + "%)";
|
||||||
|
|
||||||
return getOutputLabel(glyph, text);
|
return getOutputLabel(glyph, text);
|
||||||
|
|
|
@ -51,8 +51,10 @@ public class FontAwesome5 extends GlyphFont {
|
||||||
LINK('\uf0c1'),
|
LINK('\uf0c1'),
|
||||||
LOCK('\uf023'),
|
LOCK('\uf023'),
|
||||||
LOCK_OPEN('\uf3c1'),
|
LOCK_OPEN('\uf3c1'),
|
||||||
|
LONG_ARROW_ALT_RIGHT('\uf30b'),
|
||||||
MAGNIFYING_GLASS_PLUS('\uf00e'),
|
MAGNIFYING_GLASS_PLUS('\uf00e'),
|
||||||
MAGNIFYING_GLASS_MINUS('\uf010'),
|
MAGNIFYING_GLASS_MINUS('\uf010'),
|
||||||
|
MICROCHIP('\uf2db'),
|
||||||
MINUS_CIRCLE('\uf056'),
|
MINUS_CIRCLE('\uf056'),
|
||||||
PEN_FANCY('\uf5ac'),
|
PEN_FANCY('\uf5ac'),
|
||||||
PLUS('\uf067'),
|
PLUS('\uf067'),
|
||||||
|
|
|
@ -0,0 +1,178 @@
|
||||||
|
package com.sparrowwallet.sparrow.glyphfont;
|
||||||
|
|
||||||
|
import com.sparrowwallet.drongo.wallet.Payment;
|
||||||
|
import com.sparrowwallet.drongo.wallet.WalletTransaction;
|
||||||
|
import com.sparrowwallet.sparrow.AppServices;
|
||||||
|
import com.sparrowwallet.sparrow.control.TransactionDiagram;
|
||||||
|
import org.controlsfx.glyphfont.FontAwesome;
|
||||||
|
import org.controlsfx.glyphfont.Glyph;
|
||||||
|
|
||||||
|
public class GlyphUtils {
|
||||||
|
public static Glyph getOutputGlyph(WalletTransaction walletTx, Payment payment) {
|
||||||
|
if(payment.getType().equals(Payment.Type.MIX)) {
|
||||||
|
return getMixGlyph();
|
||||||
|
} else if(payment.getType().equals(Payment.Type.FAKE_MIX)) {
|
||||||
|
return getFakeMixGlyph();
|
||||||
|
} else if(walletTx.isConsolidationSend(payment)) {
|
||||||
|
return getConsolidationGlyph();
|
||||||
|
} else if(walletTx.isPremixSend(payment)) {
|
||||||
|
return getPremixGlyph();
|
||||||
|
} else if(walletTx.isBadbankSend(payment)) {
|
||||||
|
return getBadbankGlyph();
|
||||||
|
} else if(payment.getType().equals(Payment.Type.WHIRLPOOL_FEE)) {
|
||||||
|
return getWhirlpoolFeeGlyph();
|
||||||
|
} else if(payment instanceof TransactionDiagram.AdditionalPayment) {
|
||||||
|
return ((TransactionDiagram.AdditionalPayment)payment).getOutputGlyph(walletTx);
|
||||||
|
} else if(walletTx.getToWallet(AppServices.get().getOpenWallets().keySet(), payment) != null) {
|
||||||
|
return getDepositGlyph();
|
||||||
|
} else if(walletTx.isDuplicateAddress(payment)) {
|
||||||
|
return getPaymentWarningGlyph();
|
||||||
|
}
|
||||||
|
|
||||||
|
return getPaymentGlyph();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getPaymentGlyph() {
|
||||||
|
Glyph paymentGlyph = new Glyph("FontAwesome", FontAwesome.Glyph.SEND);
|
||||||
|
paymentGlyph.getStyleClass().add("payment-icon");
|
||||||
|
paymentGlyph.setFontSize(12);
|
||||||
|
return paymentGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getPaymentWarningGlyph() {
|
||||||
|
Glyph paymentWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.EXCLAMATION_TRIANGLE);
|
||||||
|
paymentWarningGlyph.getStyleClass().add("payment-warning-icon");
|
||||||
|
paymentWarningGlyph.setFontSize(12);
|
||||||
|
return paymentWarningGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getConsolidationGlyph() {
|
||||||
|
Glyph consolidationGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.REPLY_ALL);
|
||||||
|
consolidationGlyph.getStyleClass().add("consolidation-icon");
|
||||||
|
consolidationGlyph.setFontSize(12);
|
||||||
|
return consolidationGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getDepositGlyph() {
|
||||||
|
Glyph depositGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.ARROW_DOWN);
|
||||||
|
depositGlyph.getStyleClass().add("deposit-icon");
|
||||||
|
depositGlyph.setFontSize(12);
|
||||||
|
return depositGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getPremixGlyph() {
|
||||||
|
Glyph premixGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.RANDOM);
|
||||||
|
premixGlyph.getStyleClass().add("premix-icon");
|
||||||
|
premixGlyph.setFontSize(12);
|
||||||
|
return premixGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getBadbankGlyph() {
|
||||||
|
Glyph badbankGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.BIOHAZARD);
|
||||||
|
badbankGlyph.getStyleClass().add("badbank-icon");
|
||||||
|
badbankGlyph.setFontSize(12);
|
||||||
|
return badbankGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getWhirlpoolFeeGlyph() {
|
||||||
|
Glyph whirlpoolFeeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.HAND_HOLDING_WATER);
|
||||||
|
whirlpoolFeeGlyph.getStyleClass().add("whirlpoolfee-icon");
|
||||||
|
whirlpoolFeeGlyph.setFontSize(12);
|
||||||
|
return whirlpoolFeeGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getFakeMixGlyph() {
|
||||||
|
Glyph fakeMixGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.THEATER_MASKS);
|
||||||
|
fakeMixGlyph.getStyleClass().add("fakemix-icon");
|
||||||
|
fakeMixGlyph.setFontSize(12);
|
||||||
|
return fakeMixGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getTxoGlyph() {
|
||||||
|
return getChangeGlyph();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getMixGlyph() {
|
||||||
|
Glyph payjoinGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.RANDOM);
|
||||||
|
payjoinGlyph.getStyleClass().add("mix-icon");
|
||||||
|
payjoinGlyph.setFontSize(12);
|
||||||
|
return payjoinGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getExternalInputGlyph() {
|
||||||
|
Glyph externalGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.LONG_ARROW_ALT_RIGHT);
|
||||||
|
externalGlyph.getStyleClass().add("external-input-icon");
|
||||||
|
externalGlyph.setFontSize(12);
|
||||||
|
return externalGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getExcludeGlyph() {
|
||||||
|
Glyph excludeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.TIMES_CIRCLE);
|
||||||
|
excludeGlyph.getStyleClass().add("exclude-utxo");
|
||||||
|
excludeGlyph.setFontSize(12);
|
||||||
|
return excludeGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getChangeGlyph() {
|
||||||
|
Glyph changeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.COINS);
|
||||||
|
changeGlyph.getStyleClass().add("change-icon");
|
||||||
|
changeGlyph.setFontSize(12);
|
||||||
|
return changeGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getChangeWarningGlyph() {
|
||||||
|
Glyph changeWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.EXCLAMATION_TRIANGLE);
|
||||||
|
changeWarningGlyph.getStyleClass().add("change-warning-icon");
|
||||||
|
changeWarningGlyph.setFontSize(12);
|
||||||
|
return changeWarningGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getChangeReplaceGlyph() {
|
||||||
|
Glyph changeReplaceGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.ARROW_DOWN);
|
||||||
|
changeReplaceGlyph.getStyleClass().add("change-replace-icon");
|
||||||
|
changeReplaceGlyph.setFontSize(12);
|
||||||
|
return changeReplaceGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getFeeGlyph() {
|
||||||
|
Glyph feeGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.HAND_HOLDING);
|
||||||
|
feeGlyph.getStyleClass().add("fee-icon");
|
||||||
|
feeGlyph.setFontSize(12);
|
||||||
|
return feeGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getWarningGlyph() {
|
||||||
|
Glyph feeWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.EXCLAMATION_CIRCLE);
|
||||||
|
feeWarningGlyph.getStyleClass().add("fee-warning-icon");
|
||||||
|
feeWarningGlyph.setFontSize(12);
|
||||||
|
return feeWarningGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getQuestionGlyph() {
|
||||||
|
Glyph feeWarningGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.QUESTION_CIRCLE);
|
||||||
|
feeWarningGlyph.getStyleClass().add("question-icon");
|
||||||
|
feeWarningGlyph.setFontSize(12);
|
||||||
|
return feeWarningGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getLockGlyph() {
|
||||||
|
Glyph lockGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.LOCK);
|
||||||
|
lockGlyph.getStyleClass().add("lock-icon");
|
||||||
|
lockGlyph.setFontSize(12);
|
||||||
|
return lockGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getUserGlyph() {
|
||||||
|
Glyph userGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.USER);
|
||||||
|
userGlyph.getStyleClass().add("user-icon");
|
||||||
|
userGlyph.setFontSize(12);
|
||||||
|
return userGlyph;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Glyph getOpcodeGlyph() {
|
||||||
|
Glyph userGlyph = new Glyph(FontAwesome5.FONT_NAME, FontAwesome5.Glyph.MICROCHIP);
|
||||||
|
userGlyph.getStyleClass().add("opcode-icon");
|
||||||
|
userGlyph.setFontSize(12);
|
||||||
|
return userGlyph;
|
||||||
|
}
|
||||||
|
}
|
|
@ -437,8 +437,11 @@ public class HeadersController extends TransactionFormController implements Init
|
||||||
updateFee(feeAmt);
|
updateFee(feeAmt);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
headersForm.walletTransactionProperty().addListener((observable, oldValue, walletTransaction) -> {
|
||||||
|
transactionDiagram.update(walletTransaction);
|
||||||
|
});
|
||||||
transactionDiagram.labelProperty().set(transactionDiagramLabel);
|
transactionDiagram.labelProperty().set(transactionDiagramLabel);
|
||||||
transactionDiagram.update(getWalletTransaction(headersForm.getInputTransactions()));
|
headersForm.setWalletTransaction(getWalletTransaction(headersForm.getInputTransactions()));
|
||||||
|
|
||||||
blockchainForm.managedProperty().bind(blockchainForm.visibleProperty());
|
blockchainForm.managedProperty().bind(blockchainForm.visibleProperty());
|
||||||
|
|
||||||
|
@ -1334,7 +1337,7 @@ public class HeadersController extends TransactionFormController implements Init
|
||||||
if(headersForm.getInputTransactions() != null) {
|
if(headersForm.getInputTransactions() != null) {
|
||||||
allFetchedInputTransactions.putAll(headersForm.getInputTransactions());
|
allFetchedInputTransactions.putAll(headersForm.getInputTransactions());
|
||||||
}
|
}
|
||||||
transactionDiagram.update(getWalletTransaction(allFetchedInputTransactions));
|
headersForm.setWalletTransaction(getWalletTransaction(allFetchedInputTransactions));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1500,7 +1503,7 @@ public class HeadersController extends TransactionFormController implements Init
|
||||||
updateType();
|
updateType();
|
||||||
updateSize();
|
updateSize();
|
||||||
updateFee(headersForm.getPsbt().getFee());
|
updateFee(headersForm.getPsbt().getFee());
|
||||||
transactionDiagram.update(getWalletTransaction(headersForm.getInputTransactions()));
|
headersForm.setWalletTransaction(getWalletTransaction(headersForm.getInputTransactions()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1597,7 +1600,7 @@ public class HeadersController extends TransactionFormController implements Init
|
||||||
public void psbtReordered(PSBTReorderedEvent event) {
|
public void psbtReordered(PSBTReorderedEvent event) {
|
||||||
if(event.getPsbt().equals(headersForm.getPsbt())) {
|
if(event.getPsbt().equals(headersForm.getPsbt())) {
|
||||||
updateTxId();
|
updateTxId();
|
||||||
transactionDiagram.update(getWalletTransaction(headersForm.getInputTransactions()));
|
headersForm.setWalletTransaction(getWalletTransaction(headersForm.getInputTransactions()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -12,6 +12,7 @@ import com.sparrowwallet.drongo.wallet.Wallet;
|
||||||
import com.sparrowwallet.sparrow.EventManager;
|
import com.sparrowwallet.sparrow.EventManager;
|
||||||
import com.sparrowwallet.sparrow.control.*;
|
import com.sparrowwallet.sparrow.control.*;
|
||||||
import com.sparrowwallet.sparrow.event.*;
|
import com.sparrowwallet.sparrow.event.*;
|
||||||
|
import com.sparrowwallet.sparrow.glyphfont.GlyphUtils;
|
||||||
import javafx.collections.MapChangeListener;
|
import javafx.collections.MapChangeListener;
|
||||||
import javafx.fxml.FXML;
|
import javafx.fxml.FXML;
|
||||||
import javafx.fxml.Initializable;
|
import javafx.fxml.Initializable;
|
||||||
|
@ -124,7 +125,7 @@ public class InputController extends TransactionFormController implements Initia
|
||||||
inputForm.signingWalletProperty().addListener((observable, oldValue, signingWallet) -> {
|
inputForm.signingWalletProperty().addListener((observable, oldValue, signingWallet) -> {
|
||||||
updateInputLegendFromWallet(txInput, signingWallet);
|
updateInputLegendFromWallet(txInput, signingWallet);
|
||||||
});
|
});
|
||||||
updateInputLegendFromWallet(txInput, inputForm.getSigningWallet());
|
updateInputLegendFromWallet(txInput, inputForm.getWallet());
|
||||||
|
|
||||||
initializeInputFields(txInput, psbtInput);
|
initializeInputFields(txInput, psbtInput);
|
||||||
initializeScriptFields(txInput, psbtInput);
|
initializeScriptFields(txInput, psbtInput);
|
||||||
|
@ -142,19 +143,19 @@ public class InputController extends TransactionFormController implements Initia
|
||||||
return "Input #" + txInput.getIndex();
|
return "Input #" + txInput.getIndex();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateInputLegendFromWallet(TransactionInput txInput, Wallet signingWallet) {
|
private void updateInputLegendFromWallet(TransactionInput txInput, Wallet wallet) {
|
||||||
String baseText = getLegendText(txInput);
|
String baseText = getLegendText(txInput);
|
||||||
if(signingWallet != null) {
|
if(wallet != null) {
|
||||||
if(inputForm.isWalletTxo()) {
|
if(inputForm.isWalletTxo()) {
|
||||||
inputFieldset.setText(baseText + " from " + signingWallet.getFullDisplayName());
|
inputFieldset.setText(baseText + " from " + wallet.getFullDisplayName());
|
||||||
inputFieldset.setIcon(TransactionDiagram.getTxoGlyph());
|
inputFieldset.setIcon(GlyphUtils.getTxoGlyph());
|
||||||
} else {
|
} else {
|
||||||
inputFieldset.setText(baseText + " - External");
|
inputFieldset.setText(baseText + (txInput.isCoinBase() ? " - Coinbase" : " - External"));
|
||||||
inputFieldset.setIcon(TransactionDiagram.getMixGlyph());
|
inputFieldset.setIcon(GlyphUtils.getMixGlyph());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
inputFieldset.setText(baseText);
|
inputFieldset.setText(baseText + (txInput.isCoinBase() ? " - Coinbase" : " - External"));
|
||||||
inputFieldset.setIcon(null);
|
inputFieldset.setIcon(GlyphUtils.getExternalInputGlyph());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,14 +1,20 @@
|
||||||
package com.sparrowwallet.sparrow.transaction;
|
package com.sparrowwallet.sparrow.transaction;
|
||||||
|
|
||||||
import com.sparrowwallet.drongo.protocol.TransactionInput;
|
import com.sparrowwallet.drongo.protocol.TransactionInput;
|
||||||
|
import com.sparrowwallet.drongo.protocol.TransactionOutPoint;
|
||||||
import com.sparrowwallet.drongo.protocol.TransactionOutput;
|
import com.sparrowwallet.drongo.protocol.TransactionOutput;
|
||||||
import com.sparrowwallet.drongo.psbt.PSBTInput;
|
import com.sparrowwallet.drongo.psbt.PSBTInput;
|
||||||
import com.sparrowwallet.drongo.wallet.BlockTransaction;
|
import com.sparrowwallet.drongo.wallet.BlockTransaction;
|
||||||
|
import com.sparrowwallet.drongo.wallet.BlockTransactionHashIndex;
|
||||||
|
import com.sparrowwallet.sparrow.glyphfont.GlyphUtils;
|
||||||
import com.sparrowwallet.sparrow.net.ElectrumServer;
|
import com.sparrowwallet.sparrow.net.ElectrumServer;
|
||||||
import javafx.fxml.FXMLLoader;
|
import javafx.fxml.FXMLLoader;
|
||||||
import javafx.scene.Node;
|
import javafx.scene.Node;
|
||||||
|
import javafx.scene.control.Label;
|
||||||
|
import org.controlsfx.glyphfont.Glyph;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.util.Optional;
|
||||||
|
|
||||||
public class InputForm extends IndexedTransactionForm {
|
public class InputForm extends IndexedTransactionForm {
|
||||||
public InputForm(TransactionData txdata, PSBTInput psbtInput) {
|
public InputForm(TransactionData txdata, PSBTInput psbtInput) {
|
||||||
|
@ -48,7 +54,7 @@ public class InputForm extends IndexedTransactionForm {
|
||||||
|
|
||||||
public boolean isWalletTxo() {
|
public boolean isWalletTxo() {
|
||||||
TransactionInput txInput = getTransactionInput();
|
TransactionInput txInput = getTransactionInput();
|
||||||
return getSigningWallet() != null && getSigningWallet().isWalletTxo(txInput);
|
return getWallet() != null && getWallet().isWalletTxo(txInput);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -67,6 +73,24 @@ public class InputForm extends IndexedTransactionForm {
|
||||||
}
|
}
|
||||||
|
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "Input #" + getIndex();
|
TransactionOutPoint outPoint = getTransactionInput().getOutpoint();
|
||||||
|
return outPoint.getHash().toString().substring(0, 8) + "..:" + outPoint.getIndex();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Label getLabel() {
|
||||||
|
if(getWalletTransaction() != null) {
|
||||||
|
TransactionOutPoint outPoint = getTransactionInput().getOutpoint();
|
||||||
|
Optional<BlockTransactionHashIndex> optRef = getWalletTransaction().getSelectedUtxos().keySet().stream()
|
||||||
|
.filter(txo -> txo.getHash().equals(outPoint.getHash()) && txo.getIndex() == outPoint.getIndex()).findFirst();
|
||||||
|
Glyph inputGlyph = isWalletTxo() ? GlyphUtils.getTxoGlyph() : (getWallet() != null ? GlyphUtils.getMixGlyph() : GlyphUtils.getExternalInputGlyph());
|
||||||
|
if(optRef.isPresent() && optRef.get().getLabel() != null) {
|
||||||
|
return new Label(optRef.get().getLabel(), inputGlyph);
|
||||||
|
} else {
|
||||||
|
return new Label(toString(), inputGlyph);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return super.getLabel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,8 +5,8 @@ import com.sparrowwallet.drongo.address.Address;
|
||||||
import com.sparrowwallet.drongo.protocol.NonStandardScriptException;
|
import com.sparrowwallet.drongo.protocol.NonStandardScriptException;
|
||||||
import com.sparrowwallet.drongo.protocol.TransactionInput;
|
import com.sparrowwallet.drongo.protocol.TransactionInput;
|
||||||
import com.sparrowwallet.drongo.protocol.TransactionOutput;
|
import com.sparrowwallet.drongo.protocol.TransactionOutput;
|
||||||
import com.sparrowwallet.drongo.wallet.BlockTransaction;
|
import com.sparrowwallet.drongo.wallet.*;
|
||||||
import com.sparrowwallet.drongo.wallet.Wallet;
|
import com.sparrowwallet.sparrow.AppServices;
|
||||||
import com.sparrowwallet.sparrow.EventManager;
|
import com.sparrowwallet.sparrow.EventManager;
|
||||||
import com.sparrowwallet.sparrow.control.*;
|
import com.sparrowwallet.sparrow.control.*;
|
||||||
import com.sparrowwallet.sparrow.event.PSBTReorderedEvent;
|
import com.sparrowwallet.sparrow.event.PSBTReorderedEvent;
|
||||||
|
@ -66,7 +66,10 @@ public class OutputController extends TransactionFormController implements Initi
|
||||||
outputForm.signingWalletProperty().addListener((observable, oldValue, signingWallet) -> {
|
outputForm.signingWalletProperty().addListener((observable, oldValue, signingWallet) -> {
|
||||||
updateOutputLegendFromWallet(txOutput, signingWallet);
|
updateOutputLegendFromWallet(txOutput, signingWallet);
|
||||||
});
|
});
|
||||||
updateOutputLegendFromWallet(txOutput, outputForm.getSigningWallet());
|
outputForm.walletTransactionProperty().addListener((observable, oldValue, walletTransaction) -> {
|
||||||
|
updateOutputLegendFromWallet(txOutput, walletTransaction != null ? walletTransaction.getWallet() : null);
|
||||||
|
});
|
||||||
|
updateOutputLegendFromWallet(txOutput, outputForm.getWallet());
|
||||||
|
|
||||||
value.setValue(txOutput.getValue());
|
value.setValue(txOutput.getValue());
|
||||||
to.setVisible(false);
|
to.setVisible(false);
|
||||||
|
@ -103,23 +106,40 @@ public class OutputController extends TransactionFormController implements Initi
|
||||||
return "Output #" + txOutput.getIndex();
|
return "Output #" + txOutput.getIndex();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateOutputLegendFromWallet(TransactionOutput txOutput, Wallet signingWallet) {
|
private void updateOutputLegendFromWallet(TransactionOutput txOutput, Wallet wallet) {
|
||||||
String baseText = getLegendText(txOutput);
|
String baseText = getLegendText(txOutput);
|
||||||
if(signingWallet != null) {
|
WalletTransaction walletTx = outputForm.getWalletTransaction();
|
||||||
|
if(walletTx != null) {
|
||||||
|
List<WalletTransaction.Output> outputs = walletTx.getOutputs();
|
||||||
|
if(outputForm.getIndex() < outputs.size()) {
|
||||||
|
WalletTransaction.Output output = outputs.get(outputForm.getIndex());
|
||||||
|
if(output instanceof WalletTransaction.NonAddressOutput) {
|
||||||
|
outputFieldset.setText(baseText);
|
||||||
|
} else if(output instanceof WalletTransaction.PaymentOutput paymentOutput) {
|
||||||
|
Payment payment = paymentOutput.getPayment();
|
||||||
|
Wallet toWallet = walletTx.getToWallet(AppServices.get().getOpenWallets().keySet(), payment);
|
||||||
|
WalletNode toNode = walletTx.getWallet() != null && !walletTx.getWallet().isBip47() ? walletTx.getAddressNodeMap().get(payment.getAddress()) : null;
|
||||||
|
outputFieldset.setText(baseText + (toWallet == null ? (toNode != null ? " - Consolidation" : " - Payment") : " - Received to " + toWallet.getFullDisplayName()));
|
||||||
|
} else if(output instanceof WalletTransaction.ChangeOutput changeOutput) {
|
||||||
|
outputFieldset.setText(baseText + " - Change to " + changeOutput.getWalletNode().toString());
|
||||||
|
} else {
|
||||||
|
outputFieldset.setText(baseText);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
outputFieldset.setText(baseText);
|
||||||
|
}
|
||||||
|
} else if(wallet != null) {
|
||||||
if(outputForm.isWalletChange()) {
|
if(outputForm.isWalletChange()) {
|
||||||
outputFieldset.setText(baseText + " - Change");
|
outputFieldset.setText(baseText + " - Change");
|
||||||
outputFieldset.setIcon(TransactionDiagram.getChangeGlyph());
|
|
||||||
} else if(outputForm.isWalletConsolidation()) {
|
} else if(outputForm.isWalletConsolidation()) {
|
||||||
outputFieldset.setText(baseText + " - Consolidation");
|
outputFieldset.setText(baseText + " - Consolidation");
|
||||||
outputFieldset.setIcon(TransactionDiagram.getConsolidationGlyph());
|
|
||||||
} else {
|
} else {
|
||||||
outputFieldset.setText(baseText + " - Payment");
|
outputFieldset.setText(baseText + " - Payment");
|
||||||
outputFieldset.setIcon(TransactionDiagram.getPaymentGlyph());
|
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
outputFieldset.setText(baseText);
|
outputFieldset.setText(baseText);
|
||||||
outputFieldset.setIcon(null);
|
|
||||||
}
|
}
|
||||||
|
outputFieldset.setIcon(outputForm.getLabel().getGraphic());
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateSpent(List<BlockTransaction> outputTransactions) {
|
private void updateSpent(List<BlockTransaction> outputTransactions) {
|
||||||
|
|
|
@ -1,12 +1,20 @@
|
||||||
package com.sparrowwallet.sparrow.transaction;
|
package com.sparrowwallet.sparrow.transaction;
|
||||||
|
|
||||||
import com.sparrowwallet.drongo.KeyPurpose;
|
import com.sparrowwallet.drongo.KeyPurpose;
|
||||||
|
import com.sparrowwallet.drongo.address.Address;
|
||||||
|
import com.sparrowwallet.drongo.protocol.ScriptChunk;
|
||||||
|
import com.sparrowwallet.drongo.protocol.ScriptOpCodes;
|
||||||
import com.sparrowwallet.drongo.protocol.TransactionOutput;
|
import com.sparrowwallet.drongo.protocol.TransactionOutput;
|
||||||
import com.sparrowwallet.drongo.psbt.PSBTOutput;
|
import com.sparrowwallet.drongo.psbt.PSBTOutput;
|
||||||
|
import com.sparrowwallet.drongo.wallet.Payment;
|
||||||
|
import com.sparrowwallet.drongo.wallet.WalletTransaction;
|
||||||
|
import com.sparrowwallet.sparrow.glyphfont.GlyphUtils;
|
||||||
import javafx.fxml.FXMLLoader;
|
import javafx.fxml.FXMLLoader;
|
||||||
import javafx.scene.Node;
|
import javafx.scene.Node;
|
||||||
|
import javafx.scene.control.Label;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.util.*;
|
||||||
|
|
||||||
public class OutputForm extends IndexedTransactionForm {
|
public class OutputForm extends IndexedTransactionForm {
|
||||||
public OutputForm(TransactionData txdata, PSBTOutput psbtOutput) {
|
public OutputForm(TransactionData txdata, PSBTOutput psbtOutput) {
|
||||||
|
@ -26,15 +34,15 @@ public class OutputForm extends IndexedTransactionForm {
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isWalletConsolidation() {
|
public boolean isWalletConsolidation() {
|
||||||
return (getSigningWallet() != null && getSigningWallet().getWalletOutputScripts(KeyPurpose.RECEIVE).containsKey(getTransactionOutput().getScript()));
|
return (getWallet() != null && getWallet().getWalletOutputScripts(KeyPurpose.RECEIVE).containsKey(getTransactionOutput().getScript()));
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isWalletChange() {
|
public boolean isWalletChange() {
|
||||||
return (getSigningWallet() != null && getSigningWallet().getWalletOutputScripts(getSigningWallet().getChangeKeyPurpose()).containsKey(getTransactionOutput().getScript()));
|
return (getWallet() != null && getWallet().getWalletOutputScripts(getWallet().getChangeKeyPurpose()).containsKey(getTransactionOutput().getScript()));
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isWalletPayment() {
|
public boolean isWalletPayment() {
|
||||||
return getSigningWallet() != null;
|
return getWallet() != null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -53,6 +61,33 @@ public class OutputForm extends IndexedTransactionForm {
|
||||||
}
|
}
|
||||||
|
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "Output #" + getIndex();
|
Address address = getTransactionOutput().getScript().getToAddress();
|
||||||
|
return address != null ? address.toString() : "Output #" + getIndex();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Label getLabel() {
|
||||||
|
if(getWalletTransaction() != null) {
|
||||||
|
List<WalletTransaction.Output> outputs = getWalletTransaction().getOutputs();
|
||||||
|
if(getIndex() < outputs.size()) {
|
||||||
|
WalletTransaction.Output output = outputs.get(getIndex());
|
||||||
|
if(output instanceof WalletTransaction.NonAddressOutput) {
|
||||||
|
List<ScriptChunk> chunks = output.getTransactionOutput().getScript().getChunks();
|
||||||
|
if(!chunks.isEmpty() && chunks.get(0).isOpCode() && chunks.get(0).getOpcode() == ScriptOpCodes.OP_RETURN) {
|
||||||
|
return new Label(chunks.get(0).toString(), GlyphUtils.getOpcodeGlyph());
|
||||||
|
} else {
|
||||||
|
return new Label("Output #" + getIndex(), GlyphUtils.getOpcodeGlyph());
|
||||||
|
}
|
||||||
|
} else if(output instanceof WalletTransaction.PaymentOutput paymentOutput) {
|
||||||
|
Payment payment = paymentOutput.getPayment();
|
||||||
|
return new Label(payment.getLabel() != null && payment.getType() != Payment.Type.FAKE_MIX && payment.getType() != Payment.Type.MIX ? payment.getLabel() : payment.getAddress().toString(),
|
||||||
|
GlyphUtils.getOutputGlyph(getWalletTransaction(), payment));
|
||||||
|
} else if(output instanceof WalletTransaction.ChangeOutput changeOutput) {
|
||||||
|
return new Label(changeOutput.getWalletNode().getAddress().toString(), GlyphUtils.getChangeGlyph());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return super.getLabel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,7 +10,6 @@ import com.sparrowwallet.drongo.wallet.Wallet;
|
||||||
import com.sparrowwallet.sparrow.AppServices;
|
import com.sparrowwallet.sparrow.AppServices;
|
||||||
import com.sparrowwallet.sparrow.EventManager;
|
import com.sparrowwallet.sparrow.EventManager;
|
||||||
import com.sparrowwallet.sparrow.TransactionTabData;
|
import com.sparrowwallet.sparrow.TransactionTabData;
|
||||||
import com.sparrowwallet.sparrow.control.TransactionDiagram;
|
|
||||||
import com.sparrowwallet.sparrow.control.TransactionHexArea;
|
import com.sparrowwallet.sparrow.control.TransactionHexArea;
|
||||||
import com.sparrowwallet.sparrow.event.*;
|
import com.sparrowwallet.sparrow.event.*;
|
||||||
import com.sparrowwallet.sparrow.io.Config;
|
import com.sparrowwallet.sparrow.io.Config;
|
||||||
|
@ -20,6 +19,7 @@ import javafx.fxml.FXML;
|
||||||
import javafx.fxml.Initializable;
|
import javafx.fxml.Initializable;
|
||||||
import javafx.scene.Node;
|
import javafx.scene.Node;
|
||||||
import javafx.scene.Parent;
|
import javafx.scene.Parent;
|
||||||
|
import javafx.scene.control.Label;
|
||||||
import javafx.scene.control.TreeCell;
|
import javafx.scene.control.TreeCell;
|
||||||
import javafx.scene.control.TreeItem;
|
import javafx.scene.control.TreeItem;
|
||||||
import javafx.scene.control.TreeView;
|
import javafx.scene.control.TreeView;
|
||||||
|
@ -158,28 +158,11 @@ public class TransactionController implements Initializable {
|
||||||
setContextMenu(null);
|
setContextMenu(null);
|
||||||
|
|
||||||
if(form != null) {
|
if(form != null) {
|
||||||
setText(form.toString());
|
Label label = form.getLabel();
|
||||||
|
label.setMaxWidth(100);
|
||||||
|
setGraphic(label);
|
||||||
|
|
||||||
if(form.getSigningWallet() != null) {
|
if(form.getSigningWallet() != null) {
|
||||||
if(form instanceof InputForm) {
|
|
||||||
InputForm inputForm = (InputForm)form;
|
|
||||||
if(inputForm.isWalletTxo()) {
|
|
||||||
setGraphic(TransactionDiagram.getTxoGlyph());
|
|
||||||
} else {
|
|
||||||
setGraphic(TransactionDiagram.getMixGlyph());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if(form instanceof OutputForm) {
|
|
||||||
OutputForm outputForm = (OutputForm)form;
|
|
||||||
if(outputForm.isWalletChange()) {
|
|
||||||
setGraphic(TransactionDiagram.getChangeGlyph());
|
|
||||||
} else if(outputForm.isWalletConsolidation()) {
|
|
||||||
setGraphic(TransactionDiagram.getConsolidationGlyph());
|
|
||||||
} else {
|
|
||||||
setGraphic(TransactionDiagram.getPaymentGlyph());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
setOnDragDetected(null);
|
setOnDragDetected(null);
|
||||||
setOnDragOver(null);
|
setOnDragOver(null);
|
||||||
setOnDragDropped(null);
|
setOnDragDropped(null);
|
||||||
|
@ -196,6 +179,10 @@ public class TransactionController implements Initializable {
|
||||||
txtree.refresh();
|
txtree.refresh();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
txdata.walletTransactionProperty().addListener((observable, oldValue, newValue) -> {
|
||||||
|
txtree.refresh();
|
||||||
|
});
|
||||||
|
|
||||||
txtree.getSelectionModel().selectedItemProperty().addListener((observable, old_val, selectedItem) -> {
|
txtree.getSelectionModel().selectedItemProperty().addListener((observable, old_val, selectedItem) -> {
|
||||||
TransactionForm transactionForm = selectedItem.getValue();
|
TransactionForm transactionForm = selectedItem.getValue();
|
||||||
if(transactionForm instanceof PageForm) {
|
if(transactionForm instanceof PageForm) {
|
||||||
|
|
|
@ -3,10 +3,7 @@ package com.sparrowwallet.sparrow.transaction;
|
||||||
import com.sparrowwallet.drongo.KeyPurpose;
|
import com.sparrowwallet.drongo.KeyPurpose;
|
||||||
import com.sparrowwallet.drongo.protocol.*;
|
import com.sparrowwallet.drongo.protocol.*;
|
||||||
import com.sparrowwallet.drongo.psbt.PSBT;
|
import com.sparrowwallet.drongo.psbt.PSBT;
|
||||||
import com.sparrowwallet.drongo.wallet.BlockTransaction;
|
import com.sparrowwallet.drongo.wallet.*;
|
||||||
import com.sparrowwallet.drongo.wallet.Keystore;
|
|
||||||
import com.sparrowwallet.drongo.wallet.Wallet;
|
|
||||||
import com.sparrowwallet.drongo.wallet.WalletNode;
|
|
||||||
import com.sparrowwallet.sparrow.io.Storage;
|
import com.sparrowwallet.sparrow.io.Storage;
|
||||||
import javafx.beans.property.SimpleObjectProperty;
|
import javafx.beans.property.SimpleObjectProperty;
|
||||||
import javafx.collections.FXCollections;
|
import javafx.collections.FXCollections;
|
||||||
|
@ -30,6 +27,7 @@ public class TransactionData {
|
||||||
private final ObservableMap<Wallet, Storage> availableWallets = FXCollections.observableHashMap();
|
private final ObservableMap<Wallet, Storage> availableWallets = FXCollections.observableHashMap();
|
||||||
private final SimpleObjectProperty<Wallet> signingWallet = new SimpleObjectProperty<>(this, "signingWallet", null);
|
private final SimpleObjectProperty<Wallet> signingWallet = new SimpleObjectProperty<>(this, "signingWallet", null);
|
||||||
private final ObservableMap<TransactionSignature, Keystore> signatureKeystoreMap = FXCollections.observableMap(new LinkedHashMap<>());
|
private final ObservableMap<TransactionSignature, Keystore> signatureKeystoreMap = FXCollections.observableMap(new LinkedHashMap<>());
|
||||||
|
private final SimpleObjectProperty<WalletTransaction> walletTransaction = new SimpleObjectProperty<>(this, "walletTransaction", null);
|
||||||
|
|
||||||
public TransactionData(String name, PSBT psbt) {
|
public TransactionData(String name, PSBT psbt) {
|
||||||
this(name, psbt.getTransaction());
|
this(name, psbt.getTransaction());
|
||||||
|
@ -179,4 +177,20 @@ public class TransactionData {
|
||||||
|
|
||||||
return signingWalletNodes;
|
return signingWalletNodes;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public WalletTransaction getWalletTransaction() {
|
||||||
|
return walletTransaction.get();
|
||||||
|
}
|
||||||
|
|
||||||
|
public SimpleObjectProperty<WalletTransaction> walletTransactionProperty() {
|
||||||
|
return walletTransaction;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setWalletTransaction(WalletTransaction walletTransaction) {
|
||||||
|
this.walletTransaction.set(walletTransaction);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Wallet getWallet() {
|
||||||
|
return getSigningWallet() != null ? getSigningWallet() : (getWalletTransaction() != null ? getWalletTransaction().getWallet() : null);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,14 +4,12 @@ import com.sparrowwallet.drongo.protocol.Sha256Hash;
|
||||||
import com.sparrowwallet.drongo.protocol.Transaction;
|
import com.sparrowwallet.drongo.protocol.Transaction;
|
||||||
import com.sparrowwallet.drongo.protocol.TransactionSignature;
|
import com.sparrowwallet.drongo.protocol.TransactionSignature;
|
||||||
import com.sparrowwallet.drongo.psbt.PSBT;
|
import com.sparrowwallet.drongo.psbt.PSBT;
|
||||||
import com.sparrowwallet.drongo.wallet.BlockTransaction;
|
import com.sparrowwallet.drongo.wallet.*;
|
||||||
import com.sparrowwallet.drongo.wallet.Keystore;
|
|
||||||
import com.sparrowwallet.drongo.wallet.Wallet;
|
|
||||||
import com.sparrowwallet.drongo.wallet.WalletNode;
|
|
||||||
import com.sparrowwallet.sparrow.io.Storage;
|
import com.sparrowwallet.sparrow.io.Storage;
|
||||||
import javafx.beans.property.SimpleObjectProperty;
|
import javafx.beans.property.SimpleObjectProperty;
|
||||||
import javafx.collections.ObservableMap;
|
import javafx.collections.ObservableMap;
|
||||||
import javafx.scene.Node;
|
import javafx.scene.Node;
|
||||||
|
import javafx.scene.control.Label;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
|
@ -98,6 +96,22 @@ public abstract class TransactionForm {
|
||||||
return txdata.getSigningWalletNodes();
|
return txdata.getSigningWalletNodes();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public WalletTransaction getWalletTransaction() {
|
||||||
|
return txdata.getWalletTransaction();
|
||||||
|
}
|
||||||
|
|
||||||
|
public SimpleObjectProperty<WalletTransaction> walletTransactionProperty() {
|
||||||
|
return txdata.walletTransactionProperty();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setWalletTransaction(WalletTransaction walletTransaction) {
|
||||||
|
txdata.setWalletTransaction(walletTransaction);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Wallet getWallet() {
|
||||||
|
return txdata.getWallet();
|
||||||
|
}
|
||||||
|
|
||||||
public boolean isEditable() {
|
public boolean isEditable() {
|
||||||
if(getBlockTransaction() != null) {
|
if(getBlockTransaction() != null) {
|
||||||
return false;
|
return false;
|
||||||
|
@ -120,4 +134,8 @@ public abstract class TransactionForm {
|
||||||
public abstract Node getContents() throws IOException;
|
public abstract Node getContents() throws IOException;
|
||||||
|
|
||||||
public abstract TransactionView getView();
|
public abstract TransactionView getView();
|
||||||
|
|
||||||
|
public Label getLabel() {
|
||||||
|
return new Label(toString());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -31,3 +31,7 @@
|
||||||
.color-8 { -fx-fill: #000000 }
|
.color-8 { -fx-fill: #000000 }
|
||||||
|
|
||||||
.color-grey { -fx-fill: #e5e5e6 }
|
.color-grey { -fx-fill: #e5e5e6 }
|
||||||
|
|
||||||
|
.change-warning-icon, .payment-warning-icon {
|
||||||
|
-fx-text-fill: rgb(238, 210, 2);
|
||||||
|
}
|
Loading…
Reference in a new issue