2022-07-13 06:37:12 +00:00
|
|
|
import React, { useState } from 'react';
|
|
|
|
import { Link } from 'react-router-dom';
|
2020-02-21 07:46:13 +00:00
|
|
|
import './light.css';
|
2022-08-23 02:54:19 +00:00
|
|
|
import { Container, Form, Grid, Header, Input } from 'semantic-ui-react';
|
2020-02-21 07:46:13 +00:00
|
|
|
import { PayPalPayNow, PayPalSubscribe } from './PayPal.js';
|
2022-08-23 02:54:19 +00:00
|
|
|
import { MembersDropdown } from './Members.js';
|
|
|
|
import { requester } from './utils.js';
|
|
|
|
|
2023-05-25 23:53:41 +00:00
|
|
|
export function PayWithProtocoin(props) {
|
2023-05-26 20:17:49 +00:00
|
|
|
const { token, user, refreshUser, amount, onSuccess, custom } = props;
|
2023-05-25 23:53:41 +00:00
|
|
|
const member = user.member;
|
|
|
|
const [error, setError] = useState({});
|
|
|
|
const [loading, setLoading] = useState(false);
|
|
|
|
const [success, setSuccess] = useState(false);
|
|
|
|
|
|
|
|
const handleSubmit = (e) => {
|
|
|
|
if (loading) return;
|
|
|
|
setSuccess(false);
|
|
|
|
setLoading(true);
|
|
|
|
|
|
|
|
const data = { amount: amount, ...custom, balance: member.protocoin };
|
|
|
|
requester('/protocoin/spend_request/', 'POST', token, data)
|
|
|
|
.then(res => {
|
|
|
|
setLoading(false);
|
|
|
|
setSuccess(true);
|
2023-05-26 20:17:49 +00:00
|
|
|
if (onSuccess) {
|
|
|
|
onSuccess();
|
|
|
|
}
|
2023-05-25 23:53:41 +00:00
|
|
|
setError({});
|
|
|
|
refreshUser();
|
|
|
|
})
|
|
|
|
.catch(err => {
|
|
|
|
setLoading(false);
|
|
|
|
console.log(err);
|
|
|
|
setError(err.data);
|
|
|
|
});
|
|
|
|
};
|
|
|
|
|
|
|
|
return (
|
|
|
|
<Form onSubmit={handleSubmit}>
|
|
|
|
<Form.Button disabled={!amount} color='green' loading={loading} error={error.amount}>
|
|
|
|
Pay with Protocoin
|
|
|
|
</Form.Button>
|
|
|
|
{success && <div>Success!</div>}
|
|
|
|
</Form>
|
|
|
|
);
|
|
|
|
};
|
|
|
|
|
2022-08-23 02:54:19 +00:00
|
|
|
export function SendProtocoin(props) {
|
|
|
|
const { token, user, refreshUser } = props;
|
|
|
|
const member = user.member;
|
|
|
|
const [input, setInput] = useState({});
|
|
|
|
const [error, setError] = useState({});
|
|
|
|
const [loading, setLoading] = useState(false);
|
|
|
|
const [success, setSuccess] = useState(false);
|
|
|
|
|
|
|
|
const handleValues = (e, v) => setInput({ ...input, [v.name]: v.value });
|
|
|
|
const handleChange = (e) => handleValues(e, e.currentTarget);
|
|
|
|
|
|
|
|
const handleSubmit = (e) => {
|
|
|
|
if (loading) return;
|
|
|
|
setSuccess(false);
|
|
|
|
setLoading(true);
|
|
|
|
|
|
|
|
const data = { ...input, balance: member.protocoin };
|
|
|
|
requester('/protocoin/send_to_member/', 'POST', token, data)
|
|
|
|
.then(res => {
|
|
|
|
setLoading(false);
|
|
|
|
setSuccess(true);
|
|
|
|
setInput({});
|
|
|
|
setError({});
|
|
|
|
refreshUser();
|
|
|
|
})
|
|
|
|
.catch(err => {
|
|
|
|
setLoading(false);
|
|
|
|
console.log(err);
|
|
|
|
setError(err.data);
|
|
|
|
});
|
|
|
|
};
|
|
|
|
|
|
|
|
const makeProps = (name) => ({
|
|
|
|
name: name,
|
|
|
|
onChange: handleChange,
|
|
|
|
value: input[name] || '',
|
|
|
|
error: error[name],
|
|
|
|
});
|
|
|
|
|
|
|
|
return (
|
|
|
|
<Form onSubmit={handleSubmit}>
|
|
|
|
<Form.Group widths='equal'>
|
|
|
|
<Form.Field error={error.member_id}>
|
|
|
|
<label>Member (search)</label>
|
|
|
|
<MembersDropdown
|
|
|
|
token={token}
|
|
|
|
{...makeProps('member_id')}
|
|
|
|
onChange={handleValues}
|
|
|
|
/>
|
|
|
|
</Form.Field>
|
|
|
|
|
|
|
|
<Form.Input
|
|
|
|
label='Amount (₱)'
|
|
|
|
fluid
|
|
|
|
{...makeProps('amount')}
|
|
|
|
/>
|
|
|
|
</Form.Group>
|
|
|
|
|
|
|
|
<Form.Button loading={loading} error={error.non_field_errors}>
|
|
|
|
Send
|
|
|
|
</Form.Button>
|
|
|
|
{success && <div>Success!</div>}
|
|
|
|
</Form>
|
|
|
|
);
|
|
|
|
};
|
2020-02-21 07:46:13 +00:00
|
|
|
|
|
|
|
export function Paymaster(props) {
|
2022-08-23 02:54:19 +00:00
|
|
|
const { token, user, refreshUser } = props;
|
2020-06-19 04:55:48 +00:00
|
|
|
const [locker, setLocker] = useState('5.00');
|
2023-05-25 23:53:41 +00:00
|
|
|
const [consumables, setConsumables] = useState('');
|
2022-08-22 22:15:03 +00:00
|
|
|
const [buyProtocoin, setBuyProtocoin] = useState('10.00');
|
2022-01-25 04:12:22 +00:00
|
|
|
const [consumablesMemo, setConsumablesMemo] = useState('');
|
2023-05-25 23:53:41 +00:00
|
|
|
const [donate, setDonate] = useState('');
|
2021-06-24 23:18:19 +00:00
|
|
|
const [memo, setMemo] = useState('');
|
2020-02-21 07:46:13 +00:00
|
|
|
|
2020-08-27 03:19:26 +00:00
|
|
|
const monthly_fees = user.member.monthly_fees || 55;
|
|
|
|
|
2020-02-21 07:46:13 +00:00
|
|
|
return (
|
|
|
|
<Container>
|
|
|
|
<Header size='large'>Paymaster</Header>
|
|
|
|
<p>Use these buttons to send money to Protospace.</p>
|
|
|
|
|
2022-08-22 22:15:03 +00:00
|
|
|
<Header size='medium'>Protocoin</Header>
|
2022-08-23 21:41:48 +00:00
|
|
|
<p>Protocoin is used to buy things from Protospace's vending machines. No cash value.</p>
|
2022-08-22 22:15:03 +00:00
|
|
|
|
2022-08-23 03:44:35 +00:00
|
|
|
<p>Current balance: ₱ {user.member.protocoin.toFixed(2)}</p>
|
2022-08-23 02:54:19 +00:00
|
|
|
|
2022-08-24 23:12:02 +00:00
|
|
|
<p>Total circulation: ₱ {user.member.total_protocoin.toFixed(2)}</p>
|
|
|
|
|
2022-08-23 02:54:19 +00:00
|
|
|
<Grid stackable padded columns={2}>
|
|
|
|
<Grid.Column width={5}>
|
2022-08-23 21:41:48 +00:00
|
|
|
Buy any amount of Protocoin:
|
2022-08-22 22:15:03 +00:00
|
|
|
|
|
|
|
<div className='pay-custom'>
|
|
|
|
<Input
|
|
|
|
fluid
|
|
|
|
label={{ basic: true, content: '$' }}
|
|
|
|
labelPosition='left'
|
|
|
|
value={buyProtocoin}
|
|
|
|
onChange={(e, v) => setBuyProtocoin(v.value)}
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
|
|
|
|
<PayPalPayNow
|
|
|
|
amount={buyProtocoin}
|
|
|
|
name='Protospace Protocoin'
|
|
|
|
custom={JSON.stringify({ category: 'Exchange', member: user.member.id })}
|
|
|
|
/>
|
2022-08-23 21:41:48 +00:00
|
|
|
|
|
|
|
<p>See a director to purchase Protocoin with a different payment method.</p>
|
2022-08-22 22:15:03 +00:00
|
|
|
</Grid.Column>
|
2022-08-23 02:54:19 +00:00
|
|
|
|
|
|
|
<Grid.Column width={8}>
|
|
|
|
<p>Send Protocoin:</p>
|
|
|
|
<SendProtocoin token={token} user={user} refreshUser={refreshUser} />
|
|
|
|
</Grid.Column>
|
2022-08-22 22:15:03 +00:00
|
|
|
</Grid>
|
|
|
|
|
2020-02-21 07:46:13 +00:00
|
|
|
<Header size='medium'>Member Dues</Header>
|
|
|
|
<Grid stackable padded columns={3}>
|
|
|
|
<Grid.Column>
|
2020-08-27 03:19:26 +00:00
|
|
|
<p>Pay ${monthly_fees}.00 once:</p>
|
2020-02-21 07:46:13 +00:00
|
|
|
<PayPalPayNow
|
2020-08-27 03:19:26 +00:00
|
|
|
amount={monthly_fees}
|
2020-02-21 07:46:13 +00:00
|
|
|
name='Protospace Membership'
|
|
|
|
custom={JSON.stringify({ member: user.member.id })}
|
|
|
|
/>
|
|
|
|
</Grid.Column>
|
|
|
|
|
|
|
|
<Grid.Column>
|
2020-08-27 03:19:26 +00:00
|
|
|
<p>Subscribe ${monthly_fees}.00 / month:</p>
|
2020-02-21 07:46:13 +00:00
|
|
|
<PayPalSubscribe
|
2020-08-27 03:19:26 +00:00
|
|
|
amount={monthly_fees}
|
2020-02-21 07:46:13 +00:00
|
|
|
name='Protospace Membership'
|
|
|
|
custom={JSON.stringify({ member: user.member.id })}
|
|
|
|
/>
|
|
|
|
</Grid.Column>
|
|
|
|
|
|
|
|
<Grid.Column>
|
2020-08-27 03:19:26 +00:00
|
|
|
<p>Pay ${monthly_fees * 11}.00 for a year:</p>
|
2020-02-21 07:46:13 +00:00
|
|
|
<PayPalPayNow
|
2020-08-27 03:19:26 +00:00
|
|
|
amount={monthly_fees * 11}
|
2020-02-21 07:46:13 +00:00
|
|
|
name='Protospace Membership'
|
|
|
|
custom={JSON.stringify({ deal: 12, member: user.member.id })}
|
|
|
|
/>
|
|
|
|
<p>...get one month for free!</p>
|
|
|
|
</Grid.Column>
|
|
|
|
</Grid>
|
|
|
|
|
2023-05-29 17:43:32 +00:00
|
|
|
<Grid stackable columns={2}>
|
|
|
|
<Grid.Column>
|
|
|
|
<Header size='medium'>Consumables</Header>
|
2020-02-21 07:46:13 +00:00
|
|
|
|
2023-05-29 17:43:32 +00:00
|
|
|
<p>Pay for materials you use (ie. welding gas, 3D printing, etc).</p>
|
2022-01-25 04:12:22 +00:00
|
|
|
|
|
|
|
Custom amount:
|
|
|
|
|
|
|
|
<div className='pay-custom'>
|
|
|
|
<Input
|
|
|
|
fluid
|
|
|
|
label={{ basic: true, content: '$' }}
|
|
|
|
labelPosition='left'
|
|
|
|
value={consumables}
|
|
|
|
onChange={(e, v) => setConsumables(v.value)}
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
|
2023-07-31 22:05:57 +00:00
|
|
|
<div className='bottomMargin'>
|
2022-01-25 04:12:22 +00:00
|
|
|
Please explain what you bought:<br/>
|
|
|
|
<Input
|
|
|
|
value={consumablesMemo}
|
|
|
|
maxLength={50}
|
|
|
|
onChange={(e, v) => setConsumablesMemo(v.value)}
|
|
|
|
/>
|
2023-07-30 23:59:16 +00:00
|
|
|
</div>
|
2022-01-25 04:12:22 +00:00
|
|
|
|
2020-02-21 07:46:13 +00:00
|
|
|
<PayPalPayNow
|
2022-01-25 04:12:22 +00:00
|
|
|
amount={consumables}
|
|
|
|
name='Protospace Consumables'
|
|
|
|
custom={JSON.stringify({ category: 'Consumables', member: user.member.id, memo: consumablesMemo })}
|
2020-02-21 07:46:13 +00:00
|
|
|
/>
|
2023-05-25 23:53:41 +00:00
|
|
|
|
|
|
|
<PayWithProtocoin
|
|
|
|
token={token} user={user} refreshUser={refreshUser}
|
|
|
|
amount={consumables}
|
2023-05-26 20:17:49 +00:00
|
|
|
onSuccess={() => setConsumables('')}
|
2023-05-25 23:53:41 +00:00
|
|
|
custom={{ category: 'Consumables', memo: consumablesMemo }}
|
|
|
|
/>
|
2020-02-21 07:46:13 +00:00
|
|
|
</Grid.Column>
|
2023-05-29 17:43:32 +00:00
|
|
|
<Grid.Column>
|
|
|
|
<Header size='medium'>Donate</Header>
|
2022-01-25 04:12:22 +00:00
|
|
|
|
2023-05-29 17:43:32 +00:00
|
|
|
<p>Donation of any amount to Protospace.</p>
|
2020-02-21 07:46:13 +00:00
|
|
|
|
2020-03-16 21:44:10 +00:00
|
|
|
Custom amount:
|
|
|
|
|
|
|
|
<div className='pay-custom'>
|
|
|
|
<Input
|
|
|
|
fluid
|
|
|
|
label={{ basic: true, content: '$' }}
|
|
|
|
labelPosition='left'
|
|
|
|
value={donate}
|
|
|
|
onChange={(e, v) => setDonate(v.value)}
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
|
2023-07-31 22:05:57 +00:00
|
|
|
<div className='bottomMargin'>
|
2022-01-25 04:12:22 +00:00
|
|
|
Optional memo:<br/>
|
|
|
|
<Input
|
|
|
|
value={memo}
|
|
|
|
maxLength={50}
|
|
|
|
onChange={(e, v) => setMemo(v.value)}
|
|
|
|
/>
|
2023-07-30 23:59:16 +00:00
|
|
|
</div>
|
2022-01-25 04:12:22 +00:00
|
|
|
|
2020-02-21 07:46:13 +00:00
|
|
|
<PayPalPayNow
|
2020-03-16 21:44:10 +00:00
|
|
|
amount={donate}
|
2020-02-21 07:46:13 +00:00
|
|
|
name='Protospace Donation'
|
2021-06-24 23:18:19 +00:00
|
|
|
custom={JSON.stringify({ category: 'Donation', member: user.member.id, memo: memo })}
|
2020-02-21 07:46:13 +00:00
|
|
|
/>
|
2023-05-25 23:53:41 +00:00
|
|
|
|
|
|
|
<PayWithProtocoin
|
|
|
|
token={token} user={user} refreshUser={refreshUser}
|
|
|
|
amount={donate}
|
2023-05-26 20:17:49 +00:00
|
|
|
onSuccess={() => setDonate('')}
|
2023-05-25 23:53:41 +00:00
|
|
|
custom={{ category: 'Donation', memo: memo }}
|
|
|
|
/>
|
2020-02-21 07:46:13 +00:00
|
|
|
</Grid.Column>
|
|
|
|
</Grid>
|
2020-06-19 04:55:48 +00:00
|
|
|
|
|
|
|
<Header size='medium'>Locker Storage</Header>
|
|
|
|
|
|
|
|
<p>Confirm location and availability with <Link to='/members/392'>Scott Young</Link> before subscribing.</p>
|
|
|
|
|
|
|
|
<Grid stackable padded columns={1}>
|
|
|
|
<Grid.Column>
|
|
|
|
Custom amount:
|
|
|
|
|
|
|
|
<div className='pay-custom'>
|
|
|
|
<Input
|
|
|
|
fluid
|
|
|
|
label={{ basic: true, content: '$' }}
|
|
|
|
labelPosition='left'
|
|
|
|
value={locker}
|
|
|
|
onChange={(e, v) => setLocker(v.value)}
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
|
|
|
|
<PayPalSubscribe
|
|
|
|
amount={locker}
|
|
|
|
name='Protospace Locker'
|
2022-03-29 22:04:04 +00:00
|
|
|
custom={JSON.stringify({ memo: 'Locker Rental', category: 'Purchases', member: user.member.id })}
|
2020-06-19 04:55:48 +00:00
|
|
|
/>
|
|
|
|
</Grid.Column>
|
|
|
|
</Grid>
|
2020-02-21 07:46:13 +00:00
|
|
|
</Container>
|
|
|
|
);
|
2023-07-31 22:05:57 +00:00
|
|
|
};
|