[dart] Upgrade to Dart 2.12 and its null-safety features
This commit is contained in:
parent
0e8e894056
commit
291fc9111b
@ -5,7 +5,7 @@ homepage: https://labs.phundrak.com/phundrak/org-website-backend
|
||||
author: Lucien Cartier-Tilet <lucien@phundrak.com>
|
||||
|
||||
environment:
|
||||
sdk: '>=2.7.0 <3.0.0'
|
||||
sdk: '>=2.12.0 <3.0.0'
|
||||
|
||||
dependencies:
|
||||
|
||||
|
@ -35,7 +35,7 @@ final icons = {
|
||||
};
|
||||
|
||||
// Get the current page’s title
|
||||
String getPageTitle() => querySelector('title').text;
|
||||
String getPageTitle() => querySelector('title')!.text!;
|
||||
|
||||
// Create the home button
|
||||
Future<Element> makeHome() async {
|
||||
@ -45,7 +45,7 @@ Future<Element> makeHome() async {
|
||||
'afterBegin',
|
||||
Element.a()
|
||||
..attributes['href'] = '/'
|
||||
..append(makeIcon(icons['home'])));
|
||||
..append(makeIcon(icons['home']!)));
|
||||
}
|
||||
|
||||
// Create a clickable icon
|
||||
@ -61,7 +61,7 @@ Future<Element> makePages() async {
|
||||
..append(Element.a()
|
||||
..attributes['tabindex'] = '-1'
|
||||
..attributes['href'] = 'javascript:void(0)'
|
||||
..append(makeIcon(icons['pages'])))
|
||||
..append(makeIcon(icons['pages']!)))
|
||||
..classes.addAll(['nav-item', 'has-dropdown'])
|
||||
..append(Element.ul()
|
||||
..attributes['id'] = 'drop-page'
|
||||
@ -87,23 +87,23 @@ Future<Element> makeShare() async {
|
||||
..append(Element.a()
|
||||
..attributes['href'] = 'javascript:void(0)'
|
||||
..attributes['tabindex'] = '-1'
|
||||
..append(makeIcon(icons['share'])))
|
||||
..append(makeIcon(icons['share']!)))
|
||||
..append(Element.ul()
|
||||
..classes.add('dropdown')
|
||||
..attributes['id'] = 'drop-share'
|
||||
..append(makeShareLink(
|
||||
makeIcon(icons['twitter']),
|
||||
makeIcon(icons['twitter']!),
|
||||
'https://twitter.com/share?text=${getPageTitle()}'
|
||||
'&url=${window.location.href}'))
|
||||
..append(makeShareLink(makeIcon(icons['reddit']),
|
||||
..append(makeShareLink(makeIcon(icons['reddit']!),
|
||||
'https://www.reddit.com/submit?title=${getPageTitle()}s&url=${window.location.href}'))
|
||||
..append(makeShareLink(makeIcon(icons['email']),
|
||||
'mailto:?subject=${getPageTitle}&body=${window.location.href}'))
|
||||
..append(makeShareLink(makeIcon(icons['email']!),
|
||||
'mailto:?subject=$getPageTitle&body=${window.location.href}'))
|
||||
..append(makeShareLink(
|
||||
makeIcon(icons['linkedin']),
|
||||
makeIcon(icons['linkedin']!),
|
||||
'https://www.linkedin.com/shareArticle?mini=true&url=${window.location.href}'
|
||||
'&title=${getPageTitle()}'))
|
||||
..append(makeShareLink(makeIcon(icons['facebook']),
|
||||
..append(makeShareLink(makeIcon(icons['facebook']!),
|
||||
'https://www.facebook.com/sharer/sharer.php?u=${window.location.href}')));
|
||||
}
|
||||
|
||||
@ -125,7 +125,7 @@ Future<Element> makeThemeChanger() async {
|
||||
..attributes['tabindex'] = '-1'
|
||||
..append(Element.span()
|
||||
..style.verticalAlign = 'top'
|
||||
..append(makeIcon(icons['theme']))))
|
||||
..append(makeIcon(icons['theme']!))))
|
||||
..append(Element.ul()
|
||||
..classes.add('dropdown')
|
||||
..attributes['id'] = 'theme-dropdown'
|
||||
@ -144,7 +144,7 @@ Future<Element> makeToc() async {
|
||||
..append(Element.a()
|
||||
..attributes['tabindex'] = '-1'
|
||||
..attributes['href'] = 'javascript:void(0)'
|
||||
..append(makeIcon(icons['toc'])));
|
||||
..append(makeIcon(icons['toc']!)));
|
||||
}
|
||||
|
||||
// Add a navbar atop of the HTML body, containing:
|
||||
|
@ -15,29 +15,29 @@ Future<String> fetchRemoteSitemap() async {
|
||||
|
||||
// Parse the list of elements and detect pages from this list
|
||||
Map<String, String> detectPages(List<Element> t_sitemap,
|
||||
[String t_prefix, Map<String, String> t_links]) {
|
||||
[String? t_prefix, Map<String, String>? t_links]) {
|
||||
t_links ??= <String, String>{};
|
||||
|
||||
// parse each element in sitemap
|
||||
for (var elem in t_sitemap) {
|
||||
// if it’s a link
|
||||
if (elem.innerHtml.startsWith('<a')) {
|
||||
elem = elem.firstChild;
|
||||
final url = elem.attributes['href'];
|
||||
final text = elem.firstChild.text;
|
||||
if (elem.innerHtml!.startsWith('<a')) {
|
||||
elem = elem.children[0];
|
||||
final url = elem.attributes['href']!;
|
||||
final text = elem.children[0].text;
|
||||
if (excluded_keywords.contains(text) ||
|
||||
excluded_keywords.contains(url.substring(0, url.length - 5))) {
|
||||
continue;
|
||||
}
|
||||
t_links['/$url'] = (t_prefix == null) ? text : '$text ($t_prefix)';
|
||||
t_links!['/$url'] = ((t_prefix == null) ? text : '$text ($t_prefix)')!;
|
||||
} else {
|
||||
final prefix = (t_prefix == null)
|
||||
? elem.firstChild.text.replaceAll('\n', '')
|
||||
: '$t_prefix / ${elem.firstChild.text}'.replaceAll('\n', '');
|
||||
? elem.firstChild!.text!.replaceAll('\n', '')
|
||||
: '$t_prefix / ${elem.firstChild!.text}'.replaceAll('\n', '');
|
||||
t_links = detectPages(elem.children[0].children, prefix, t_links);
|
||||
}
|
||||
}
|
||||
return t_links;
|
||||
return t_links!;
|
||||
}
|
||||
|
||||
// This function returns a Map which contains all links to languages detected
|
||||
@ -45,13 +45,13 @@ Map<String, String> detectPages(List<Element> t_sitemap,
|
||||
Future<Map<String, String>> parseSitemap() async {
|
||||
final content = await fetchRemoteSitemap();
|
||||
final sitemap = Element.ul()..innerHtml = content;
|
||||
final sitemapNodes = sitemap.querySelector('ul').children;
|
||||
final sitemapNodes = sitemap.querySelector('ul')!.children;
|
||||
return detectPages(sitemapNodes);
|
||||
}
|
||||
|
||||
Future<void> createSitemap() async {
|
||||
final sitemap = await parseSitemap();
|
||||
final pages = querySelector('#drop-page');
|
||||
final pages = querySelector('#drop-page')!;
|
||||
sitemap.forEach((url, name) {
|
||||
final link = Element.li()
|
||||
..classes.add('dropdown-item')
|
||||
|
@ -13,7 +13,7 @@ Future<Element> makeHeader() async {
|
||||
..attributes['alt'] = 'Logo'
|
||||
..attributes['height'] = '150px'
|
||||
..attributes['width'] = '150px')
|
||||
..append(querySelector('h1'));
|
||||
..append(querySelector('h1')!);
|
||||
final subt = header.querySelector('.subtitle');
|
||||
if (subt != null) {
|
||||
header.append(subt);
|
||||
@ -32,8 +32,8 @@ Future<void> wrapTables() async {
|
||||
// All images that are not nested inside a link will be linkified to themselves.
|
||||
Future<void> linkifyImg() async {
|
||||
querySelectorAll('img').forEach((img) {
|
||||
if (img.parent.tagName == 'P') {
|
||||
final link = Element.a()..attributes['href'] = img.attributes['src'];
|
||||
if (img.parent!.tagName == 'P') {
|
||||
final link = Element.a()..attributes['href'] = img.attributes['src']!;
|
||||
img.insertAdjacentElement('beforeBegin', link);
|
||||
link.append(img);
|
||||
}
|
||||
@ -61,10 +61,10 @@ Future<void> reorganizeHtml() async {
|
||||
await linkifyImg();
|
||||
|
||||
// Add navbar to page
|
||||
querySelector('body').insertAdjacentElement('afterBegin', navbar);
|
||||
querySelector('body')!.insertAdjacentElement('afterBegin', navbar);
|
||||
|
||||
// Add headet to page
|
||||
querySelector('#content').insertAdjacentElement('beforeBegin', header);
|
||||
querySelector('#content')!.insertAdjacentElement('beforeBegin', header);
|
||||
|
||||
// Add correct class to TOC
|
||||
final toc = (querySelector('#table-of-contents') ??
|
||||
@ -72,7 +72,7 @@ Future<void> reorganizeHtml() async {
|
||||
..attributes['id'] = 'table-of-contents'
|
||||
..innerText = 'Table of Contents Unavailable'))
|
||||
..classes.add('dropdown');
|
||||
navbar.querySelector('#toc-drop').append(toc);
|
||||
navbar.querySelector('#toc-drop')!.append(toc);
|
||||
|
||||
// Remove all <br> tags from HTML
|
||||
querySelectorAll('br').forEach((br) => br.remove());
|
||||
|
@ -2,22 +2,19 @@ import 'dart:html' show window, querySelector;
|
||||
|
||||
final localStorage = window.localStorage;
|
||||
|
||||
Future<void> setTheme([String theme]) async {
|
||||
final currentTheme = theme ?? localStorage['theme'] ??
|
||||
() {
|
||||
final devicePrefersDark =
|
||||
window.matchMedia('(prefers-color-scheme: dark)').matches;
|
||||
return devicePrefersDark ? 'nord' : 'light';
|
||||
}();
|
||||
localStorage['theme'] = currentTheme;
|
||||
querySelector('body')
|
||||
Future<void> setTheme([String? theme]) async {
|
||||
theme ??= localStorage['theem'] ??
|
||||
(window.matchMedia('(prefers-color-scheme: dark)').matches
|
||||
? 'dark'
|
||||
: 'light');
|
||||
localStorage['theme'] = theme;
|
||||
querySelector('body')!
|
||||
..classes.clear()
|
||||
..classes.add(currentTheme);
|
||||
..classes.add(theme);
|
||||
}
|
||||
|
||||
void enableThemeChanger() {
|
||||
final themes = <String>['light', 'dark', 'nord', 'black'];
|
||||
themes.forEach((theme) =>
|
||||
querySelector('#${theme}Btn').onClick.listen((_) => setTheme(theme))
|
||||
);
|
||||
querySelector('#${theme}Btn')!.onClick.listen((_) => setTheme(theme)));
|
||||
}
|
||||
|
Reference in New Issue
Block a user