Skip to content
Merged
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
2 changes: 1 addition & 1 deletion src/common/search/search.css
Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,7 @@
}
}

@media screen and (max-width:494px) {
@media screen and (max-width: 494px) {
.filter {
display: grid;
justify-content: center;
Expand Down
94 changes: 94 additions & 0 deletions src/plays/currencyconverter/Currencyconverter.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
import PlayHeader from 'common/playlists/PlayHeader';
import { useState } from 'react';
import InputBox from './InputBox';
import useCurrencyInfo from './hooks/useCurrencyInfo';

// WARNING: Do not change the entry componenet name
function Currencyconverter(props) {
// State for input values
const [from, setFrom] = useState('bdt');
const [to, setTo] = useState('usd');
const [amount, setAmount] = useState(0);
const [convertedAmount, setConvertedAmount] = useState(0);

// Fetch currency info based on 'from' currency
const currencyInfo = useCurrencyInfo(from);
const options = Object.keys(currencyInfo);

// Function to swap 'from' and 'to' currencies
const swap = () => {
setFrom(to);
setTo(from);
setConvertedAmount(amount);
setAmount(convertedAmount);
};

// Function to convert currency
const convert = () => {
setConvertedAmount(amount * currencyInfo[to]);
};

return (
<>
<div className="play-details">
{/* Play header */}
<PlayHeader play={props} />
<div className="play-details-body">
{/* Main Container */}
<div className="w-full flex flex-wrap justify-around items-center">
<div className="border border-gray-60 rounded-lg p-5 backdrop-blur-sm bg-white/30">
<form
onSubmit={(e) => {
e.preventDefault();
convert();
}}
>
{/* Input box for 'from' currency */}
<div className="w-full mb-1">
<InputBox
amount={amount}
currencyOptions={options}
label="From"
selectCurrency={from}
onAmountChange={(amount) => setAmount(amount)}
onCurrencyChange={() => setAmount(amount)}
/>
</div>
<div className="relative w-full h-0.5">
{/* Button to swap 'from' and 'to' currencies */}
<button
className="absolute left-1/2 -translate-x-1/2 -translate-y-1/2 border-2 border-white rounded-md bg-blue-600 text-white px-2 py-0.5"
type="button"
onClick={swap}
>
SWAP
</button>
</div>
<div className="w-full mt-1 mb-4">
{/* Input box for 'to' currency */}
<InputBox
amountDisable
amount={convertedAmount}
currencyOptions={options}
label="To"
selectCurrency={to}
onCurrencyChange={(currency) => setTo(currency)}
/>
</div>
{/* Button to initiate currency conversion */}
<button
className="w-full bg-blue-600 text-white px-4 py-3 rounded-lg"
type="submit"
>
Convert {from.toUpperCase()} TO {to.toUpperCase()}
</button>
</form>
</div>
</div>
</div>
</div>
</>
);
}

export default Currencyconverter;
57 changes: 57 additions & 0 deletions src/plays/currencyconverter/InputBox.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
import { useId } from 'react';

const InputBox = ({
label,
amount,
onAmountChange,
onCurrencyChange,
currencyOptions = [],
selectCurrency = 'usd',
amountDisable = false,
currencyDisable = false,
className = ''
}) => {
// Generate a unique ID for the input field
const amountInputId = useId();

return (
<div className={`bg-white p-3 rounded-lg text-sm flex ${className}`}>
{/* Input field for the amount */}
<div className="w-1/2">
<label className="text-black/40 mb-2 inline-block" htmlFor={amountInputId}>
{label}
</label>
<input
className="outline-none w-full bg-transparent py-1.5"
disabled={amountDisable}
id={amountInputId}
placeholder="Amount"
type="number"
value={amount}
onChange={(e) => onAmountChange && onAmountChange(Number(e.target.value))}
/>
</div>

{/* Currency Selection */}
<div className="w-1/2 flex flex-wrap justify-end text-right">
<p className="text-black/40 mb-2 w-full">Currency Type</p>
{/* Dropdown for selecting currency */}
<select
className="rounded-lg px-1 py-1 bg-gray-100 cursor-pointer outline-none"
disabled={currencyDisable}
value={selectCurrency}
onChange={(e) => onCurrencyChange && onCurrencyChange(e.target.value)}
>
{/* Mapping through currency options */}
{currencyOptions.map((currency, index) => (
<option key={index} value={currency}>
{currency}
</option>
))}
</select>
</div>
</div>
);
};

export default InputBox;
34 changes: 34 additions & 0 deletions src/plays/currencyconverter/Readme.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# currencyConverter

Develop a web-based currency converter. Users input an amount and select currencies to convert. Real-time exchange rates are fetched via an API.

## Play Demographic

- Language: js
- Level: Intermediate

## Creator Information

- User: sabbir2809
- Gihub Link: https://github.com/sabbir2809
- Blog:
- Video:

## Implementation Details

- useState: Keep track of user inputs and app data.
- useEffect: Fetch exchange rates when the app starts or when the user changes currencies.
- Fetch: Get exchange rates from an online service.
- Async/Await: Wait for exchange rate data to be ready before using it.
- API: Special online service providing exchange rates.
- Tailwind: Make your app look nice without hard-coding styles.
- Custom Hooks: Reuse code for common tasks like fetching data.

## Consideration

## Resources

- React Documentation: Learn useState, useEffect, and custom hooks.
- Tailwind CSS Documentation: Style your app with utility classes.
- Async/Await in JavaScript: Handle asynchronous operations.
- API Documentation: Fetch exchange rates from APIs.
Binary file added src/plays/currencyconverter/cover.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
32 changes: 32 additions & 0 deletions src/plays/currencyconverter/hooks/useCurrencyInfo.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import { useEffect, useState } from 'react';

// Custom hook to fetch currency information
const useCurrencyInfo = (currency) => {
// State to hold currency data
const [data, setData] = useState({});

// Fetch currency data when currency changes
useEffect(() => {
fetch(
`https://cdn.jsdelivr.net/npm/@fawazahmed0/currency-api@latest/v1/currencies/${currency}.json`
)
.then((response) => {
// If not successful, throw an error
if (!response.ok) {
throw new Error('Failed to fetch currency data');
}

// Parse response JSON
return response.json();
})
.then(({ [currency]: currencyData }) => setData(currencyData))
.catch((error) => {
console.error('Error fetching currency data:', error);
});
}, [currency]); // Dependency array with currency

// Return currency data
return data;
};

export default useCurrencyInfo;
8 changes: 4 additions & 4 deletions src/plays/language-translater/Readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@ Language Translator is a web application built with React.js that allows users t

- User: Venkat-3010
- Gihub Link: https://github.com/Venkat-3010
- Blog:
- Video:
- Blog:
- Video:

## Implementation Details

Expand All @@ -31,12 +31,12 @@ The `Language Translator` is implemented with below steps.
- Translate button: Initiates the translation using `Fetch API`.
- Copy button: uses `clipboard` to copy the input and translated text.
- Listen button: Reads out the the input and translated text using `SpeechSynthesisUtterance`.
- Language Switch: Allows users to swap the source and target languages.
- Language Switch: Allows users to swap the source and target languages.

## Consideration

Update all considerations(if any)

## Resources

API source: https://mymemory.translated.net/
API source: https://mymemory.translated.net/
27 changes: 14 additions & 13 deletions src/plays/language-translater/styles.css
Original file line number Diff line number Diff line change
Expand Up @@ -115,17 +115,18 @@
}

@media (max-width: 1024px) {
.Language-Translator_body{
font-size: small;
}
.Language-Translator_container{
flex-direction: column;
align-items: center;
margin: 0;
}

.Language-Translator_sourceLang, .Language-Translator_targetLang{
width: 80vw;
height: 60%;
}
.Language-Translator_body {
font-size: small;
}
.Language-Translator_container {
flex-direction: column;
align-items: center;
margin: 0;
}

.Language-Translator_sourceLang,
.Language-Translator_targetLang {
width: 80vw;
height: 60%;
}
}