forked from airyrooms/maleo.js
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
docs(pwa-example): add example for pwa
ported google pwa example to work with maleo re airyrooms#152
- Loading branch information
Showing
34 changed files
with
1,083 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
# Maleo Progressive Web Application Example | ||
|
||
This example is ported from [Google's PWA Tutorial](https://developers.google.com/web/fundamentals/codelabs/your-first-pwapp/) to work with Maleo |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,34 @@ | ||
import React from 'react'; | ||
import { default as Document, Header, Scripts, Main } from '@airy/maleo/document'; | ||
|
||
export default class CustomDocument extends Document { | ||
render() { | ||
return ( | ||
<html> | ||
<Header> | ||
<meta charSet="utf-8" /> | ||
<meta http-equiv="X-UA-Compatible" content="IE=edge" /> | ||
<meta name="viewport" content="width=device-width, initial-scale=1.0" /> | ||
|
||
<link rel="manifest" href="/manifest.json" /> | ||
<meta name="theme-color" content="#2F3BA2" /> | ||
<title>Weather PWA</title> | ||
|
||
{/* Safari */} | ||
<meta name="apple-mobile-web-app-capable" content="yes" /> | ||
<meta name="apple-mobile-web-app-status-bar-style" content="black" /> | ||
<meta name="apple-mobile-web-app-title" content="Weather PWA" /> | ||
<link rel="apple-touch-icon" href="images/icons/icon-152x152.png" /> | ||
|
||
{/* Windows */} | ||
<meta name="msapplication-TileImage" content="images/icons/icon-144x144.png" /> | ||
<meta name="msapplication-TileColor" content="#2F3BA2" /> | ||
</Header> | ||
<body> | ||
<Main /> | ||
<Scripts /> | ||
</body> | ||
</html> | ||
); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
import React from 'react'; | ||
import Wrap from '@airy/maleo/wrap'; | ||
import pageWithStyles from '@airy/maleo-css-plugin/pageWithStyles'; | ||
|
||
@pageWithStyles | ||
export default class extends Wrap { | ||
static getInitialProps = () => { | ||
// Register Service Worker on client | ||
if (typeof window !== 'undefined') { | ||
if ('serviceWorker' in navigator) { | ||
navigator.serviceWorker.register('./sw').then(function() { | ||
console.log('Service Worker Registered'); | ||
}); | ||
} | ||
} | ||
}; | ||
} |
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
const cssPlugin = require('@airy/maleo-css-plugin'); | ||
|
||
module.exports = cssPlugin({ | ||
enableISL: true, | ||
cssLoader: { | ||
modules: true, | ||
camelCase: true, | ||
}, | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,35 @@ | ||
{ | ||
"name": "Weather", | ||
"short_name": "Weather", | ||
"icons": [ | ||
{ | ||
"src": "images/icons/icon-128x128.png", | ||
"sizes": "128x128", | ||
"type": "image/png" | ||
}, | ||
{ | ||
"src": "images/icons/icon-144x144.png", | ||
"sizes": "144x144", | ||
"type": "image/png" | ||
}, | ||
{ | ||
"src": "images/icons/icon-152x152.png", | ||
"sizes": "152x152", | ||
"type": "image/png" | ||
}, | ||
{ | ||
"src": "images/icons/icon-192x192.png", | ||
"sizes": "192x192", | ||
"type": "image/png" | ||
}, | ||
{ | ||
"src": "images/icons/icon-256x256.png", | ||
"sizes": "256x256", | ||
"type": "image/png" | ||
} | ||
], | ||
"start_url": "/", | ||
"display": "standalone", | ||
"background_color": "#3E4EB8", | ||
"theme_color": "#2F3BA2" | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
{ | ||
"name": "pwa", | ||
"version": "1.0.0", | ||
"main": "index.js", | ||
"license": "MIT", | ||
"scripts": { | ||
"dev": "maleo dev", | ||
"build": "export NODE_ENV=production && maleo build", | ||
"start": "export NODE_ENV=production && node .maleo/server.js" | ||
}, | ||
"dependencies": { | ||
"@airy/maleo": "latest", | ||
"@airy/maleo-css-plugin": "^0.1.6", | ||
"classnames": "^2.2.6", | ||
"react": "^16.8.5" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
[ | ||
{ | ||
"path": "/", | ||
"page": "./src/RootComponent" | ||
} | ||
] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
import { Server } from '@airy/maleo/server'; | ||
import path from 'path'; | ||
import express from 'express'; | ||
|
||
const PORT = process.env.PORT || 3000; | ||
|
||
const maleoServer = Server.init({ | ||
port: PORT, | ||
}); | ||
|
||
// register static image folder | ||
maleoServer.applyExpressMiddleware('/images', express.static('./images')); | ||
// register path /sw to return service worker file | ||
maleoServer.applyExpressMiddleware('/sw', (req, res, next) => { | ||
res.sendFile(path.resolve('.', 'sw.js')); | ||
}); | ||
maleoServer.applyExpressMiddleware('/manifest.json', (req, res, next) => { | ||
res.sendFile(path.resolve('.', 'manifest.json')); | ||
}); | ||
maleoServer.faviconHandler = (req, res) => { | ||
res.sendFile(path.resolve('.', 'images', 'icons', 'icon-32x32.png')); | ||
}; | ||
|
||
// example for client fetching data | ||
maleoServer.applyExpressMiddleware('/api/forecast', (req, res) => { | ||
setTimeout(() => { | ||
res.send({ | ||
query: { | ||
created: Date.parse(new Date()), | ||
result: { | ||
key: '2459115', | ||
label: 'New York, NY', | ||
created: '2016-07-22T01:00:00Z', | ||
channel: { | ||
astronomy: { | ||
sunrise: '5:43 am', | ||
sunset: '8:21 pm', | ||
}, | ||
item: { | ||
condition: { | ||
text: 'Windy', | ||
date: 'Thu, 21 Jul 2016 09:00 PM EDT', | ||
temp: 56, | ||
code: 24, | ||
}, | ||
forecast: [ | ||
{ code: 44, high: 86, low: 70 }, | ||
{ code: 44, high: 94, low: 73 }, | ||
{ code: 4, high: 95, low: 78 }, | ||
{ code: 24, high: 75, low: 89 }, | ||
{ code: 24, high: 89, low: 77 }, | ||
{ code: 44, high: 92, low: 79 }, | ||
{ code: 44, high: 89, low: 77 }, | ||
], | ||
}, | ||
atmosphere: { | ||
humidity: 56, | ||
}, | ||
wind: { | ||
speed: 25, | ||
direction: 195, | ||
}, | ||
}, | ||
}, | ||
}, | ||
}); | ||
}, 2000); | ||
}); | ||
|
||
maleoServer.run(() => { | ||
console.log('Custom Server running on port:', PORT); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,140 @@ | ||
import React from 'react'; | ||
import cn from 'classnames'; | ||
import withStyles from '@airy/maleo-css-plugin/withStyles'; | ||
|
||
import style from './style.css'; | ||
|
||
const daysOfWeek = ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun']; | ||
|
||
function Cards({ visibleCards }) { | ||
const today = new Date().getDay(); | ||
|
||
return ( | ||
<main className={style.main}> | ||
{Object.keys(visibleCards).map((card) => { | ||
const { | ||
channel: { | ||
astronomy: { sunrise, sunset }, | ||
atmosphere: { humidity }, | ||
item: { condition, forecast }, | ||
wind, | ||
}, | ||
created, | ||
key, | ||
label, | ||
} = visibleCards[card]; | ||
|
||
return ( | ||
<div key={created} className={cn(style.card, style.cardTemplate, style.weatherForecast)}> | ||
<div className={style.cityKey} /> | ||
<div className={style.cardLastUpdated} /> | ||
<div className={style.location} /> | ||
<div className={style.date}>{condition.date}</div> | ||
<div className={style.description}>{condition.text}</div> | ||
<div className={style.current}> | ||
<div className={style.visual}> | ||
<div className={cn(style.icon, getIconClass(condition.code, style))} /> | ||
<div className={style.temperature}> | ||
<span className={style.value}>{Math.round(condition.temp)}</span> | ||
<span className={style.scale}>°F</span> | ||
</div> | ||
</div> | ||
<div className={style.description}> | ||
<div className={style.humidity}>{Math.round(humidity)}%</div> | ||
<div className={style.wind}> | ||
<span className={style.value}>{Math.round(wind.speed)}</span> | ||
<span className={style.scale}>mph</span> | ||
<span className={style.direction}>{wind.direction}</span>° | ||
</div> | ||
<div className={style.sunrise}>{sunrise}</div> | ||
<div className={style.sunset}>{sunset}</div> | ||
</div> | ||
</div> | ||
<div className={style.future}> | ||
{forecast.map((fc, i) => ( | ||
<div key={i} className={style.oneday}> | ||
<div className={style.date}>{daysOfWeek[(i + today) % 7]}</div> | ||
<div className={cn(style.icon, getIconClass(fc.code, style))} /> | ||
<div className={style.tempHigh}> | ||
<span className={style.value}>{Math.round(fc.high)}</span>° | ||
</div> | ||
<br /> | ||
<div className={style.tempLow}> | ||
<span className={style.value}>{Math.round(fc.low)}</span>° | ||
</div> | ||
</div> | ||
))} | ||
</div> | ||
</div> | ||
); | ||
})} | ||
</main> | ||
); | ||
} | ||
|
||
function getIconClass(weatherCode, style) { | ||
weatherCode = parseInt(weatherCode); | ||
switch (weatherCode) { | ||
case 25: // cold | ||
case 32: // sunny | ||
case 33: // fair (night) | ||
case 34: // fair (day) | ||
case 36: // hot | ||
case 3200: // not available | ||
return style.clearDay; | ||
case 0: // tornado | ||
case 1: // tropical storm | ||
case 2: // hurricane | ||
case 6: // mixed rain and sleet | ||
case 8: // freezing drizzle | ||
case 9: // drizzle | ||
case 10: // freezing rain | ||
case 11: // showers | ||
case 12: // showers | ||
case 17: // hail | ||
case 35: // mixed rain and hail | ||
case 40: // scattered showers | ||
return style.rain; | ||
case 3: // severe thunderstorms | ||
case 4: // thunderstorms | ||
case 37: // isolated thunderstorms | ||
case 38: // scattered thunderstorms | ||
case 39: // scattered thunderstorms (not a typo) | ||
case 45: // thundershowers | ||
case 47: // isolated thundershowers | ||
return style.thunderstorms; | ||
case 5: // mixed rain and snow | ||
case 7: // mixed snow and sleet | ||
case 13: // snow flurries | ||
case 14: // light snow showers | ||
case 16: // snow | ||
case 18: // sleet | ||
case 41: // heavy snow | ||
case 42: // scattered snow showers | ||
case 43: // heavy snow | ||
case 46: // snow showers | ||
return style.snow; | ||
case 15: // blowing snow | ||
case 19: // dust | ||
case 20: // foggy | ||
case 21: // haze | ||
case 22: // smoky | ||
return style.fog; | ||
case 24: // windy | ||
case 23: // blustery | ||
return style.windy; | ||
case 26: // cloudy | ||
case 27: // mostly cloudy (night) | ||
case 28: // mostly cloudy (day) | ||
case 31: // clear (night) | ||
return style.cloudy; | ||
case 29: // partly cloudy (night) | ||
case 30: // partly cloudy (day) | ||
case 44: // partly cloudy | ||
return style.partlyCloudyDay; | ||
default: | ||
return ''; | ||
} | ||
} | ||
|
||
export default withStyles(style)(Cards); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
import React from 'react'; | ||
import withStyles from '@airy/maleo-css-plugin/withStyles'; | ||
|
||
import style from './style.css'; | ||
|
||
export function Dialog({ toggleAddDialog, addCity, selectedCity, changeSelectedCity, cities }) { | ||
return ( | ||
<div className={style.dialogContainer}> | ||
<div className={style.dialog}> | ||
<div className={style.dialogTitle}>Add new city</div> | ||
<div className={style.dialogBody}> | ||
<select | ||
value={selectedCity} | ||
onChange={changeSelectedCity} | ||
onClick={() => console.log('asd')}> | ||
{cities.map(({ value, city }) => ( | ||
<option key={value} value={value}> | ||
{city} | ||
</option> | ||
))} | ||
</select> | ||
</div> | ||
<div className={style.dialogButtons}> | ||
<button id={style.butAddCity} className={style.button} onClick={addCity}> | ||
Add | ||
</button> | ||
<button | ||
id={style.butAddCancel} | ||
className={style.button} | ||
onClick={toggleAddDialog.bind(null, false)}> | ||
Cancel | ||
</button> | ||
</div> | ||
</div> | ||
</div> | ||
); | ||
} | ||
|
||
export default withStyles(style)(Dialog); |
Oops, something went wrong.