kniazkov.dev

Case · Open-source contribution

Serbian learning app: import/export and a redesign as a PWA

A public learning app for Serbian on GitHub: words with pronunciation, lessons, dialogues, tests and the alphabet – a single HTML file without a build step. I contributed two pull requests, and both were merged: a page for sharing your own learning materials and a redesign into an installable web app.

The learning app on a computer and on a phone (demo data, interface translated into English)
Role
Contributions via pull requests
Period
10/2026
Status
2 of 2 pull requests merged
Stack
HTML · CSS · JavaScript · PWA
2 / 2pull requests merged
≈ 1,500lines changed – still without a build step
10+new features: dark mode, search, daily goal …
Offlineinstallable as an app, works without internet

Video: how the app works

Video · English · 1:52

A tour of the app

Learning, tests, dialogues, import and export, dark mode and offline mode – in English, with an AI voice-over.

Starting point

  • A public learning app on GitHub for anyone learning Serbian: words by topic with pronunciation, lessons with mini tests, dialogues, tests and the alphabet.
  • Technically a single HTML file with JavaScript, no build step and no server – progress and your own content live in the browser (localStorage).
  • You could add your own topics and lessons but not share them with others; on a computer the interface was a narrow phone-sized column.

Pull request 1: sharing your own materials – import and export

  • New “My materials” page: all your own topics, dialogues and lessons, with selection and deletion.
  • Export as one JSON bundle – download it, copy it as text or send it via the phone’s share menu.
  • Import from a file or by pasting: understands the bundle and the old single formats, shows what will be added beforehand, skips invalid entries and asks what to do with duplicates: replace or skip.
  • Security: lessons contain HTML. Since they can now come from other people, imported HTML is sanitised – no <script>, no on* handlers and no javascript: links.
Import: preview with a topic and a dialogue, below it the button to import
Import: the app shows what will be added – here a topic and a dialogue.
My materials after the import: selection and export as a file or JSON
After the import: select your own materials and share them as a file or JSON.

Pull request 2: redesign into an installable web app

Design

  • New design system: colour tokens, the Manrope typeface, cards, shadows and calm animations.
  • Dark mode: automatic like the system, light or dark.
  • Phone: bottom navigation bar; computer (from 900 px): side menu and wide grids.
  • Feedback while learning: animations for right and wrong answers, confetti for a good result.
Home screen after
Home screen before
BeforeAfter
Home screen before and after – drag the slider.

New features

  • “Back” works: every screen has its own address, and reloading no longer jumps to the home screen.
  • Daily goal with a progress ring, a learning streak and a “word of the day”.
  • Search across all words – even without special characters: “dovidjenja” finds “doviđenja”.
  • Review mistakes: a separate test made of the words you got wrong; best result per topic.
  • Latin or Cyrillic script – switchable in the settings or right on the flashcard.
  • Pronunciation check via the microphone (Web Speech API), swipes on the phone, keyboard shortcuts on the computer, a four-week activity calendar.

PWA

  • Manifest and icons: the app can be installed on phones and computers.
  • Service worker: it works without internet – words you have already listened to play offline too.
The app on a phone: home screen, flashcard, test and dark mode
On the phone: bottom navigation, flashcard, test and dark mode.

How I worked

With Claude Code: I read the app’s code and split the changes into two separate pull requests – each with a description and a checklist. Tested: every screen at 375 px width, the desktop at 1280 px, back and forward in the browser, reloading on every screen, starting offline via the service worker – and that old progress from localStorage is kept. The app stays plain HTML and JavaScript without a build step, so others can keep editing it as before.

Screenshots from the app with demo data. I translated the interface (originally in Russian) into English for this portfolio; the pull request descriptions on GitHub are in Russian.

What I bring

  • Getting into someone else’s code quickly and contributing cleanly – with well-scoped, well-described pull requests.
  • Frontend and UX: responsive design, dark mode, PWA and offline support – without a framework or a build step.
  • Thinking about security: content from other people is checked and sanitised before it is displayed.

Open to a new position

Let’s talk.

I am looking for a permanent role in AI automation, development or AI video production – remote or on site in my region.

I usually reply within 24 h
WhatsAppCV