Coded with HTML
, SCSS
, TypeScript
Built with Webpack
This is a solution to the Todo app challenge on Frontend Mentor.
The challenge is to build out a todo list and get it looking as close to the design as possible.
See task.md for more details about the task.
Users should be able to:
- View the optimal layout for the app depending on their device's screen size
- See hover states for all interactive elements on the page
- Add new todos to the list
- Mark todos as complete
- Delete todos from the list
- Filter by all/active/complete todos
- Clear all completed todos
- Toggle light and dark mode
- Bonus: Drag and drop to reorder items on the list
- HTML5
- Semantic HTML
- SASS
- Flexbox
- BEM methodology
- Responsive design
- Desktop first
- NodeJS
- TypeScript
- Webpack
- Github Pages
- Hosting
Command | Description |
---|---|
npm install |
Installs required npm packages. Run it before building the project |
npm start |
Builds application in development mode, launches a server that opens in a new browser tab |
npm run dev |
Builds application in development mode, results may be found in ./build folder |
npm run build |
Builds application in production mode, results may be found in ./build folder. Files are minimized, hash added to filenames to help when dealing with caching |
npm run lint |
Doesn't build anything. Checks code quality |
Path | Description |
---|---|
build |
Folder with files generated by Webpack |
static |
Folder with static assets (images, favicon) |
__tests__ |
Folder with Gherkin tests (manual, no automation) |
src |
Source files needed for application development |
src / index.scss |
Main styles |
src / index.ts |
Main file with TS |
src / scripts |
Definition of TS classes |
docs |
Folder with additional information, documentation |
docs / design |
Folder with images of how the interface must look like |
docs / results |
Folder with screenshots of how the application works after being fully developed |
docs / unused assets |
Folder with assets from initial FrontendMentor archive that I didn't use |
docs / README-template.md |
Template for README.md, don't use it (from FrontendMentor) |
docs / style-guide.md |
Style information: color palette, fonts, etc. (from FrontendMentor) |
docs / task.md |
Detailed task description (from FrontendMentor) |
docs / todo-app-main.zip |
Initial archive provided by Frontend Mentor |
LICENSE |
MIT License |
package-lock.json |
JSON file that keeps track of the exact version of every package that is installed so that a product is 100% reproducible in the same way even if packages are updated by their maintainers |
package.json |
JSON file that holds various metadata relevant to the project. This file is used to give information to npm that allows it to identify the project as well as handle the project's dependencies |
tsconfig.json |
JSON file that holds different compiler options for TypeScript |
.prettierrc |
Config for Prettier VS Code plugin |
.eslintrc.js |
Config for ESlint |
webpack.common.js |
Contains configuration common for build and dev configs |
webpack.dev.js |
Contains configuration for development mode |
webpack.prod.js |
Contains configuration for production mode |
Package | Comment |
---|---|
webpack |
Module bundler |
webpack-cli |
Required for work of webpack with v4 or later |
webpack-merge |
Helps to merge configs (webpack.common.js + webpack.dev.js for example) |
webpack-dev-server |
Launches developer server that automatically applies all changes in code |
typescript |
Is used by ts-loader, compiles ts into js |
ts-loader |
Is used by Webpack, compiles ts into js, resolves imports |
node-sass |
Is used by sass-loader, compiles sass/scss into css |
sass-loader |
Is used by Webpack, compiles sass/scss into css |
css-loader |
Is used by Webpack, resolves assets imported in css files, unites them in one file |
css‑minimizer‑webpack‑plugin |
Is used by Webpack, minifies css |
mini-css-extract-plugin |
Extracts transpiled css in a separate css file |
html-loader |
Is used by Webpack, resolves assets in html files. (Mode production works perfectly without it, but development mode for some reason sometimes loses some assets referred in html...) |
html‑webpack‑plugin |
Is used by Webpack, generates a html file from a template. Minifies html, adds links to js, css |
terser-webpack-plugin |
Is used by Webpack, minifies js (comes with webpack, no need to install it separately) |
eslint |
Checks code quality |
eslint-config-prettier |
Removes formatting checks that contradict to the standards of prettier |
eslint-config-standard-with-typescript
eslint-plugin-import
eslint-plugin-n
eslint-plugin-promise |
Come with ESLint |
Yeah, baby! I configured Webpack. That's a module bundler. It took much time, comparable with the time required to code the todo list itself.
Now it takes all my ts files and compiles them into one js file. Then it minifies the js file
Also it transpiles scss files into css, resolves all imports, generates hashes for all imports, and adds styles in style tag of index.html
Also it turns my template html into index.html, adds there links to js file, resolves all relative imports to assets with hash names
Also it works differently depending on mode. In production mode it minifies everything. In development it doesn't
Also it places all built files in a build folder. And clears the results of the previous build after every build
Also now it launches the server and automatically opens it in a new tab and automatically tracks all changes in files. Just use "npm run start"
Also it took many hours of reading articles, watching videos in order to properly configure it
I'm fully satisfied
P.S. Tried to make Webpack place all generated assets (images, svg, webp) in a separate folder inside of build
. Used file-loader
, but it ocurred that it's outdated, works with errors. I couldn't find any alternatives, so everything is placed automatically now in one place: in build
folder.
I have finally accomplised the task, that every beginner frontend developer must complete. Todo list! With many, many features
You can
- Add new items + submit validation
- Check / Uncheck items
- Delete individual items
- Delete all completed (checked) items
- Display all, active, completed items
- Drag and drop items
Theme is saved in local storage. Initially, if there is no theme in the storage, I use the prefers-color-scheme
to define the system theme of a user.
// If the theme is saved in local storage take it from there
const isDarkModeFromStorage = JSON.parse(
localStorage.getItem('isDarkMode') ?? 'null'
);
if (isDarkModeFromStorage) this._isDarkMode = isDarkModeFromStorage;
// Otherwise use theme from user's system settings
else
this._isDarkMode =
window.matchMedia &&
window.matchMedia('(prefers-color-scheme: dark)').matches;
I also save the todo list items and their order in local storage. Thus after page refresh data doesn't disappear.
Users can toggle dark and light theme. The default theme is defined using prefers-color-scheme
.
Classic CSS class toggle on/of to enable/disable dark theme.
I use a free version of FrontendMentor. Thus I don't have access to Figma prototypes. But that's not a problem - I made my own one
Here it is: https://www.figma.com/file/4dFzGRjZoRp0v3ed84Xrci/Todo-App
That helped me to make the application look quite appealing and to experiment with elements to come up with the best looking variant
I thought about including Jest to add unit test my scripts, but in this case it seems redundant. All functions are tightly related to the DOM elements and depend on their state. Thus it's extremely difficult to test this functions in isolations.
So instead I decided to add Gherkin "Given When Then" scenarios to describe the business logic. I wrote them prior to coding the implemenation. They describe how the interface must work with as few as possible interface details like "press button" and so on.
Feature: Switch a theme
In order to see the theme I like
As a User
I want to be able to switch themes
Scenario Outline: Switch theme
Given Current theme is <CurrentTheme>
When User switches a theme
Then System shows a <NewTheme>
Examples:
| CurrentTheme | NewTheme |
|-----------------------|-------------|
| light theme (default) | dark theme |
| dark theme | light theme |
- Submit button is disabled when input is empty
- Hover effect on items
- Theme changing icon changes depending on the current theme
- Added nice background, minified it by converting images to webp format. From 1.5 md it went to about 50 Kb!
- The interface lags for some reason when there are more than 10 items on the screen. Don't know why it happens. Even hover animation lags! Inexplicable
- Item height adapts to the length of content, so a user may input strings of any length. Don't think there is any validation needed in this case.
- If the list is empty the block "No items to display" is shown
- Added a nice frosted ice effect from IOS
- Changed the initial design of application described in the task, using Figma
- Webpack tutorial - Great tutorial about configuring Webpack!
- Prettier: VS Code plugin
- Snippets and Syntax Highlight for Gherkin (Cucumber): VS Code plugin
- Frontend Mentor - @GrbnvAlex
- Telegram - @Arlagonix
- Github - @arlagonix