Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
85 changes: 70 additions & 15 deletions apps/namadillo/src/App/Transfer/ShieldedPropertiesTooltip.tsx
Original file line number Diff line number Diff line change
@@ -1,15 +1,35 @@
import { Tooltip } from "@namada/components";
import clsx from "clsx";
import { useMemo } from "react";
import { BsEye, BsEyeSlash } from "react-icons/bs";
import semiTransparentEye from "./assets/semi-transparent-eye.svg";
import shieldedEye from "./assets/shielded-eye.svg";
import transparentEye from "./assets/transparent-eye.svg";
import { isShieldedAddress } from "./common";

type TransactionType = "transparent" | "semi-transparent" | "shielded";

export const ShieldedPropertiesTooltip = ({
sourceAddress,
destinationAddress,
}: {
sourceAddress: string | undefined;
destinationAddress: string | undefined;
}): JSX.Element => {
const isSourceShielded = isShieldedAddress(sourceAddress ?? "");
const isDestShielded = isShieldedAddress(destinationAddress ?? "");

// Determine transaction type
const transactionType: TransactionType = useMemo(() => {
if (isSourceShielded && isDestShielded) {
return "shielded";
} else if (!isSourceShielded && !isDestShielded) {
return "transparent";
} else {
return "semi-transparent";
}
}, [isSourceShielded, isDestShielded]);

const visible = useMemo((): JSX.Element => {
return (
<span className="flex items-center gap-2">
Expand All @@ -28,32 +48,67 @@ export const ShieldedPropertiesTooltip = ({
);
}, []);

const shieldedTransfer =
isShieldedAddress(sourceAddress ?? "") &&
isShieldedAddress(destinationAddress ?? "");
const shieldingTransfer =
isShieldedAddress(destinationAddress ?? "") &&
!isShieldedAddress(sourceAddress ?? "");
// Determine visibility for each property based on transaction type
const senderVisible = transactionType !== "shielded" && !isSourceShielded;
const recipientVisible = transactionType === "transparent" || !isDestShielded;
const assetVisible = transactionType !== "shielded";
const amountVisible = transactionType !== "shielded";

// Transaction type header
const transactionTypeHeader = useMemo(() => {
return (
<div className="flex items-center justify-center gap-2 bg-neutral-800 rounded-sm py-2 px-4">
<span
className={clsx(
"text-sm font-medium",
transactionType === "shielded" && "text-yellow-400"
)}
>
{transactionType === "shielded" ?
"Shielded"
: transactionType === "semi-transparent" ?
"Semi-transparent"
: "Transparent"}
</span>
<img
src={
transactionType === "shielded" ? shieldedEye
: transactionType === "semi-transparent" ?
semiTransparentEye
: transparentEye
}
alt={
transactionType === "shielded" ? "Shielded"
: transactionType === "semi-transparent" ?
"Semi-transparent"
: "Transparent"
}
className="w-4 h-4"
/>
</div>
);
}, [transactionType]);

return (
<Tooltip position="top" className="z-50 rounded-lg -mt-2">
<div className="min-w-[15rem] py-2 space-y-3">
<p className="text-white text-sm font-medium">Transaction Privacy:</p>
<div className="min-w-[18rem] py-3 space-y-3">
{transactionTypeHeader}

<div className="flex w-full items-center justify-between">
<span className="text-neutral-400 text-sm">Sender address</span>
{shieldedTransfer ? hidden : visible}
</div>
<div className="flex w-full items-center justify-between">
<span className="text-neutral-400 text-sm">Recipient address</span>
{shieldingTransfer || shieldedTransfer ? hidden : visible}
{senderVisible ? visible : hidden}
</div>
<div className="flex w-full items-center justify-between">
<span className="text-neutral-400 text-sm">Asset</span>
{shieldedTransfer ? hidden : visible}
{assetVisible ? visible : hidden}
</div>
<div className="flex w-full items-center justify-between">
<span className="text-neutral-400 text-sm">Amount</span>
{shieldedTransfer ? hidden : visible}
{amountVisible ? visible : hidden}
</div>
<div className="flex w-full items-center justify-between">
<span className="text-neutral-400 text-sm">Destination address</span>
{recipientVisible ? visible : hidden}
</div>
</div>
</Tooltip>
Expand Down
28 changes: 18 additions & 10 deletions apps/namadillo/src/App/Transfer/TransferDestination.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,9 @@ import { useLocation } from "react-router-dom";
import { Address } from "types";
import namadaShieldedIcon from "./assets/namada-shielded.svg";
import namadaTransparentIcon from "./assets/namada-transparent.svg";
import semiTransparentEye from "./assets/semi-transparent-eye.svg";
import shieldedEye from "./assets/shielded-eye.svg";
import transparentEye from "./assets/transparent-eye.svg";
import { ConnectProviderButton } from "./ConnectProviderButton";
import { CustomAddressForm } from "./CustomAddressForm";
import { DestinationAddressModal } from "./DestinationAddressModal";
Expand Down Expand Up @@ -124,20 +126,26 @@ export const TransferDestination = ({
undefined
: destinationAddress;

const isShieldedTransfer =
isShieldedNamAddress(sourceAddress ?? "") &&
isShieldedNamAddress(destinationAddress ?? "");
const isShieldingTransfer =
!isShieldedNamAddress(sourceAddress ?? "") &&
isShieldedNamAddress(destinationAddress ?? "");

const sourceWallet =
isNamadaAddress(destinationAddress || "") ? wallets.namada : wallets.keplr;
const addressType =
isShieldedAddress ? "shielded"
: isTransparentAddress(destinationAddress ?? "") ? "transparent"
: "ibc";

// Determine transaction type for eye icon
const isSourceShielded = isShieldedNamAddress(sourceAddress ?? "");
const isDestShielded = isShieldedNamAddress(destinationAddress ?? "");
const transactionType =
isSourceShielded && isDestShielded ? "shielded"
: !isSourceShielded && !isDestShielded ? "transparent"
: "semi-transparent";

const eyeIcon =
transactionType === "shielded" ? shieldedEye
: transactionType === "semi-transparent" ? semiTransparentEye
: transparentEye;

return (
<>
<div
Expand All @@ -152,11 +160,11 @@ export const TransferDestination = ({
<div>
<div className="flex justify-between items-center mb-5">
<h4 className="text-neutral-500">Destination</h4>
{(isShieldedTransfer || isShieldingTransfer) && (
{sourceAddress && destinationAddress && (
<div className="relative w-fit group/tooltip ml-auto">
<img
src={shieldedEye}
alt="Shielded Logo"
src={eyeIcon}
alt="Privacy Info"
className="w-5 mb-2 select-none cursor-pointer"
/>
<ShieldedPropertiesTooltip
Expand Down
1 change: 0 additions & 1 deletion apps/namadillo/src/App/Transfer/TransferSource.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -125,7 +125,6 @@ export const TransferSource = ({
"text-center [&_input]:text-center [&_input]:text-3xl [&_input]:bg-transparent",
"[&_input]:!border-0 [&_input]:px-0"
)}
disabled={!asset}
value={amount}
onChange={(e) => onChangeAmount?.(e.target.value)}
placeholder="Amount"
Expand Down
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 2 additions & 1 deletion apps/namadillo/src/App/Transfer/assets/shielded-eye.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
5 changes: 5 additions & 0 deletions apps/namadillo/src/App/Transfer/assets/transparent-eye.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.