Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
iOS Scriptable Widget for current Air Quality / Pollution in your city #stayhealthy #enjoyfreshair #stopcancer.
// ***Air Quality Widget***
//
// Copyright (C) 2020 by ChristophObermeier
//
// Permission to use, copy, modify, and/or distribute this software is hereby granted.
// However you have to respect the Terms of Service of the Air Quality Open Data Platform: https://aqicn.org/api/tos/
//
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER
// IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
// OF THIS SOFTWARE.
//
// Variables used by Scriptable.
// These must be at the very top of the file. Do not edit.
// icon-color: deep-green; icon-glyph: cloud;
//** Script for scriptable to get the current Air Polution of your city
//Thank you World Air Quality Index Project for gathering all the data!
// AQI Logo
const logoImg = await getImage('AQI-logo.png');
//AQI Scale and Color Legend
const url = "https://aqicn.org/scale/"
function createWidget(keyword, aqi, date, url){
let widget = new ListWidget()
let title = widget.addText([keyword] + " Air Quality")
title.font = Font.boldSystemFont(12);
title.centerAlignText();
title.minimumScaleFactor = 0.5;
title.lineLimit = 2;
widget.addSpacer();
let row = widget.addStack();
row.layoutHorizontally();
row.addSpacer(12);
const aqiLogo = row.addImage(logoImg);
aqiLogo.imageSize = new Size(12, 12);
row.addSpacer(5)
let aqiTitle = row.addText("Air Quality Index");
aqiTitle.font = Font.regularSystemFont(10);
aqiTitle.textColor = Color.black();
aqiTitle.centerAlignText();
aqiTitle.minimumScaleFactor = 0.5;
//Air Quality Levels
let aqiText = widget.addText(aqi);
aqiText.font = Font.boldSystemFont(40);
aqiText.centerAlignText();
aqiText.minimumScaleFactor = 1;
if (aqi >= 300) {
aqiText.textColor = Color.white();
widget.backgroundColor = new Color("#7e0023");
let aqiText1 = widget.addText("HAZARDOUS:๐Ÿ˜ท๐Ÿ ");
aqiText1.font = Font.boldSystemFont(10);
aqiText1.textColor = Color.white();
aqiText1.centerAlignText();
aqiText1.minimumScaleFactor = 1;
} else if (aqi >= 201) {
aqiText.textColor = Color.white();
widget.backgroundColor = new Color("#660099");
let aqiText1 = widget.addText("VERY UNHEALTHY:๐Ÿ‘ต๐Ÿฝ๐Ÿ‘ถ๐Ÿผ@๐Ÿ ");
aqiText1.font = Font.boldSystemFont(8);
aqiText1.textColor = Color.white();
aqiText1.centerAlignText();
aqiText1.minimumScaleFactor = 0.7;
} else if (aqi >= 151) {
aqiText.textColor = Color.white();
widget.backgroundColor = new Color("#cc0033");
let aqiText1 = widget.addText("UNHEALTHY:โฑโ€“>๐Ÿ ");
aqiText1.font = Font.boldSystemFont(10);
aqiText1.textColor = Color.white();
aqiText1.centerAlignText();
aqiText1.minimumScaleFactor = 0.8;
} else if (aqi >= 101) {
aqiText.textColor = Color.white();
widget.backgroundColor = new Color("#ff9933");
let aqiText1 = widget.addText("โ˜ ๏ธ sensitive groupsโ€“>๐Ÿ ");
aqiText1.font = Font.boldSystemFont(10);
aqiText1.textColor = Color.white();
aqiText1.centerAlignText();
aqiText1.minimumScaleFactor = 0.7;
} else if (aqi >= 51) {
aqiText.textColor = Color.white();
widget.backgroundColor = new Color("#ffde33");
let aqiText1 = widget.addText("MODERATE:๐Ÿ‘ถ๐Ÿคง๐Ÿ”œ๐Ÿ ");
aqiText1.font = Font.boldSystemFont(10);
aqiText1.textColor = Color.white();
aqiText1.centerAlignText();
aqiText1.minimumScaleFactor = 0.7;
} else if (aqi >= 0) {
aqiText.textColor = Color.white();
widget.backgroundColor = new Color("#009966");
let aqiText1 = widget.addText("GOOD:๐Ÿ•๐Ÿšถ๐Ÿป๐Ÿƒ๐Ÿฝโ€โ™€๏ธ๐Ÿšด๐Ÿปโ€โ™€๏ธ");
aqiText1.font = Font.boldSystemFont(10);
aqiText1.textColor = Color.white();
aqiText1.centerAlignText();
} else {
aqiText.textColor = Color.red();
widget.backgroundColor = Color.white();
}
//Last Update of Data
let dateText = widget.addText(date + " (loc. time)");
dateText.font = Font.regularSystemFont(6);
dateText.centerAlignText();
dateText.minimumScaleFactor = 0.3;
widget.addSpacer();
//Thx World Air Quality Project
let Text = widget.addText("๐Ÿ™๐ŸฝWorld Air Quality Project");
Text.font = Font.boldSystemFont(5);
Text.textColor = Color.black();
Text.centerAlignText();
Text.minimumScaleFactor = 0.4;
return widget;
}
//Get City from Air Quality Open Data Platform
async function getData(keyword) {
let req = new Request(`https://api.waqi.info/search/?keyword=${keyword}&token=19b71483eb9ddd3831a5e83312cd860fb00fa03d`)
req.method = "GET"
let response = await req.loadJSON()
if (Object.keys(response.data).length != 0) {
var result = '{"aqi" : "'+response.data[0].aqi+'", "date" : "'+response.data[0].time.stime+'"}'
} else {
var result = '{"aqi" : "N/A", "date" : "k. A."}'
}
return result
}
//Search Keyword in Air Quality Open Database
if (config.runsInApp) {
// Demo in-App visit https://aqicn.org/ for more cities
let keyword = "Milan"
let data = await getData(keyword)
data = JSON.parse(data)
let widget = createWidget(keyword, data.aqi, data.date)
Safari.open(url)
widget.presentSmall()
} else {
// Not in-App - use of fixed Parameter
let keyword = args.widgetParameter
let data = await getData(keyword)
data = JSON.parse(data)
let widget = createWidget(keyword, data.aqi, data.date)
Safari.open(url)
Script.setWidget(widget)
}
// Get and save Logo
async function getImage(logo) {
let fm = FileManager.local()
let dir = fm.documentsDirectory()
let path = fm.joinPath(dir, logo)
if (fm.fileExists(path)) {
return fm.readImage(path)
} else {
// download once
let imageUrl
switch (logo) {
case 'AQI-logo.png':
imageUrl = "https://waqi.info/icons/logo.png";
break
default:
console.log(`Sorry, couldn't find ${logo}.`);
break
}
let iconImage = await loadImage(imageUrl)
fm.writeImage(path, iconImage)
return iconImage
}
}
// helps to download an image from a given url
async function loadImage(imgUrl) {
console.log('loadImage')
const req = new Request(imgUrl)
return await req.loadImage()
}
Script.complete()
@ChristophObermeier

This comment has been minimized.

Copy link
Owner Author

@ChristophObermeier ChristophObermeier commented Nov 18, 2020

Introduction

The World Air Quality Index project is a non-profit project started in 2007. Its mission is to promote air pollution awareness for citizens and provide a unified and world-wide air quality information.

The project is providing transparent air quality information for more than 130 countries, covering more than 30,000 stations in 2000 major cities, via those two websites: aqicn.org and waqi.info.

For more info visit: https://aqicn.org/contact/ or https://waqi.info

Requirements

  • Apple Device with iOS 14.
  • Scriptable latest.

Setup

  1. Get Your City here.
  2. Copy the source code ("raw").
  3. Open Scriptable.
  4. Select "+" and insert the copy of the script.
  5. Choose the title of the script (e. g. Air Quality).
  6. Save with "Done".
  7. Back to the iOS Homescreen and get into the "wiggle mode".
  8. Press the "+" symbol and look for "Scriptable" (Liste ist alphabetisch).
    9 Choose widget size (small) and "Add widget".
  9. Go into the settings of the widget.
  10. Choose script of step #5.
  11. Define the "Parameter", e. g. "Munich" or "Berlin" -> (you can double-check here.)
    Scriptable_Para_Setting

Disclaimer

For private use only! Please enjoy responsibly :)

FAQs

Changelog

31.12.2020
  • Link to AQI Scale added -> Touch the widget to get there.
  • AQI-Logo added.

22.12.2020 10:52

  • Icon added.
  • Minor styling changes.

18.11.2020 18:20

18.11.2020 15:30

  • First Draft.

Credits

Thaaaaaank youuuuuu @simonbs for Scriptable.app and @marco79cgn for you great widgets!
For more widgets visit: Scriptables.net
Download with ScriptDude
@Necriso

This comment has been minimized.

Copy link

@Necriso Necriso commented Dec 16, 2020

Thanks for info.
Updated links at scriptables.net / scriptables.de

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment