Add Protogarden image to Home stats

This commit is contained in:
Tanner Collin 2022-05-17 02:38:20 +00:00
parent 152107a9bb
commit adb14f5c4f
6 changed files with 85 additions and 10 deletions

View File

@ -192,6 +192,42 @@ def process_image_upload(upload, crop):
return small, medium, large return small, medium, large
GARDEN_MEDIUM_SIZE = 500
def process_garden_image(upload):
try:
pic = Image.open(upload)
except OSError:
raise serializers.ValidationError(dict(non_field_errors='Invalid image file.'))
logging.debug('Detected format: %s', pic.format)
if pic.format == 'PNG':
ext = '.png'
elif pic.format == 'JPEG':
ext = '.jpg'
else:
raise serializers.ValidationError(dict(non_field_errors='Image must be a jpg or png.'))
pic = ImageOps.exif_transpose(pic)
draw = ImageDraw.Draw(pic)
timestamp = now_alberta_tz().strftime('%a %b %-d, %Y %-I:%M %p')
font = ImageFont.truetype('DejaVuSans.ttf', 60)
draw.text((10, 10), timestamp, (0,0,0), font=font)
large = 'garden-large' + ext
pic.save(STATIC_FOLDER + large)
medium = 'garden-medium' + ext
pic.thumbnail([GARDEN_MEDIUM_SIZE, GARDEN_MEDIUM_SIZE], Image.ANTIALIAS)
pic.save(STATIC_FOLDER + medium)
return medium, large
CARD_TEMPLATE_FILE = 'misc/member_card_template.jpg' CARD_TEMPLATE_FILE = 'misc/member_card_template.jpg'
CARD_PHOTO_SIZE = 425 CARD_PHOTO_SIZE = 425
CARD_PHOTO_MARGIN_TOP = 75 CARD_PHOTO_MARGIN_TOP = 75

View File

@ -857,7 +857,6 @@ class StatsViewSet(viewsets.ViewSet, List):
month_total=month_total, month_total=month_total,
)) ))
@action(detail=False, methods=['post']) @action(detail=False, methods=['post'])
def autoscan(self, request): def autoscan(self, request):
if 'autoscan' not in request.data: if 'autoscan' not in request.data:
@ -866,6 +865,18 @@ class StatsViewSet(viewsets.ViewSet, List):
cache.set('autoscan', request.data['autoscan']) cache.set('autoscan', request.data['autoscan'])
return Response(200) return Response(200)
@action(detail=False, methods=['post'])
def garden(self, request):
if 'photo' not in request.data:
raise exceptions.ValidationError(dict(photo='This field is required.'))
photo = request.data['photo']
medium, large = utils.process_garden_image(photo)
logging.debug('Wrote garden images to %s and %s', medium, large)
return Response(200)
class MemberCountViewSet(Base, List): class MemberCountViewSet(Base, List):
pagination_class = None pagination_class = None

View File

@ -27,6 +27,7 @@ import { Subscribe } from './PayPal.js';
import { PasswordReset, ConfirmReset } from './PasswordReset.js'; import { PasswordReset, ConfirmReset } from './PasswordReset.js';
import { NotFound, PleaseLogin } from './Misc.js'; import { NotFound, PleaseLogin } from './Misc.js';
import { Debug } from './Debug.js'; import { Debug } from './Debug.js';
import { Garden } from './Garden.js';
import { Footer } from './Footer.js'; import { Footer } from './Footer.js';
const APP_VERSION = 3; // TODO: automate this const APP_VERSION = 3; // TODO: automate this
@ -263,6 +264,10 @@ function App() {
<Classes token={token} user={user} refreshUser={refreshUser} /> <Classes token={token} user={user} refreshUser={refreshUser} />
</Route> </Route>
<Route path='/garden'>
<Garden />
</Route>
{user && user.member.set_details ? {user && user.member.set_details ?
<Switch> <Switch>
<Route path='/account'> <Route path='/account'>

15
webclient/src/Garden.js Normal file
View File

@ -0,0 +1,15 @@
import React, { useState, useEffect, useReducer, useContext } from 'react';
import { BrowserRouter as Router, Switch, Route, Link, useParams, useHistory } from 'react-router-dom';
import { Button, Container, Checkbox, Dimmer, Divider, Dropdown, Form, Grid, Header, Icon, Image, Menu, Message, Segment, Table } from 'semantic-ui-react';
import { apiUrl, statusColor, BasicTable, staticUrl, requester } from './utils.js';
import { NotFound } from './Misc.js';
export function Garden(props) {
return (
<Container>
<Header size='large'>Protogarden</Header>
<Image src={staticUrl + '/garden-large.jpg'} />
</Container>
);
};

View File

@ -351,6 +351,12 @@ export function Home(props) {
<SignForm token={token} /> <SignForm token={token} />
<p>Protogarden:</p>
<Link to='/garden'>
<Image src={staticUrl + '/garden-medium.jpg'} />
</Link>
</Segment> </Segment>
} }
</Grid.Column> </Grid.Column>

View File

@ -36,6 +36,7 @@ export function SignForm(props) {
<Form onSubmit={handleSubmit}> <Form onSubmit={handleSubmit}>
<p>Send a message to the sign:</p> <p>Send a message to the sign:</p>
<Form.Group>
<Form.Input <Form.Input
name='sign' name='sign'
onChange={handleChange} onChange={handleChange}
@ -46,6 +47,7 @@ export function SignForm(props) {
<Form.Button loading={loading} error={error.non_field_errors}> <Form.Button loading={loading} error={error.non_field_errors}>
Submit Submit
</Form.Button> </Form.Button>
</Form.Group>
{success && <div>Success!</div>} {success && <div>Success!</div>}
</Form> </Form>
); );