A desktop Anki add-on that brings AnkiDroid's powerful JavaScript template API to Anki Desktop, enabling advanced interactive card templates with programmatic control over the reviewer, TTS, card actions, and more.
Tags: javascript api ankidroid templates tts interactive programming developer mobile-compatibility text-to-speech card-templates reviewer-control
This add-on implements the AnkiDroidJS API for desktop Anki, providing:
- Get card counts (new, learning, review)
- Access card metadata (ID, type, interval, ease factor, etc.)
- Retrieve review statistics (reps, lapses, due date)
- Check card flags and marks
- Mark/unmark cards
- Toggle flags (red, orange, green, blue, pink, turquoise, purple)
- Bury cards and notes
- Suspend cards and notes
- Reset card progress
- Set custom due dates
- Search for cards
- Check if displaying answer
- Programmatically show answer
- Answer cards with specific ease (Again/Hard/Good/Easy)
- Speak text with customizable language, pitch, and rate
- Check if TTS is currently speaking
- Stop TTS playback
- Detect night mode status
- Show toast messages
- Enable/disable scrollbars
- Get note tags
- Set note tags (add/remove/replace)
- Check network metered status
This add-on requires Anki Desktop to be installed separately. It is designed to work with:
- Anki 2.1.50+ (recommended: Anki 2.1.60 or later)
- Python 3.9+ (included with modern Anki versions)
Important: This add-on extends Anki Desktop and does not include Anki itself. You must download and install Anki separately from apps.ankiweb.net.
License Note: Anki Desktop is licensed under the GNU Affero General Public License v3.0 (AGPL-3.0). However, per Anki's plugin policy, add-ons may use any license and are not subject to the AGPL requirements.
- Open Anki Desktop
- Go to Tools → Add-ons → Get Add-ons
- Enter code:
1035866113 - Restart Anki
- Download the latest release from GitHub Releases
- Open Anki Desktop
- Go to Tools → Add-ons → Install from file
- Select the downloaded
.ankiaddonfile - Restart Anki
-
Clone this repository:
git clone https://github.com/gallaway-jp/AnkiJSApi.git cd AnkiJSApi -
Create a symbolic link to your Anki addons folder:
Windows:
mklink /D "%APPDATA%\Anki2\addons21\ankidroid_js_api" "path\to\ankidroid-js-api-desktop\src\ankidroid_js_api"
macOS/Linux:
ln -s "$(pwd)/src/ankidroid_js_api" "$HOME/.local/share/Anki2/addons21/ankidroid_js_api"
-
Restart Anki
Initialize the API in your card template's script section:
<script>
// Initialize the API
const api = AnkiDroidJS.init({
developer: "your-email@example.com",
version: "0.0.3"
});
// Use the API
async function loadCardInfo() {
const cardId = await api.ankiGetCardId();
const reps = await api.ankiGetCardReps();
console.log(`Card ${cardId} has been reviewed ${reps} times`);
}
loadCardInfo();
</script><!-- Front Template -->
<div class="question">{{Front}}</div>
<button onclick="playTTS()">🔊 Speak</button>
<div id="stats"></div>
<script>
const api = AnkiDroidJS.init({
developer: "learner@example.com",
version: "0.0.3"
});
async function playTTS() {
await api.ankiTtsSpeak("{{Front}}", 0);
}
async function showStats() {
const newCards = await api.ankiGetNewCardCount();
const revCards = await api.ankiGetRevCardCount();
const eta = await api.ankiGetETA();
document.getElementById('stats').innerHTML =
`${newCards} new, ${revCards} review, ${eta} min remaining`;
}
showStats();
</script>
<!-- Back Template -->
{{FrontSide}}
<hr>
<div class="answer">{{Back}}</div>
<button onclick="markDifficult()">Mark Difficult</button>
<script>
async function markDifficult() {
await api.ankiToggleFlag("red");
await api.ankiShowToast("Flagged as difficult");
}
</script>See the API documentation for complete reference, or browse the full documentation.
- Anki Desktop: 2.1.50+
- API Version: 0.0.3
- Python: 3.9+
ankidroid-js-api-desktop/
├── src/
│ └── ankidroid_js_api/
│ ├── __init__.py # Add-on entry point
│ ├── api_bridge.py # JavaScript API bridge
│ ├── card_info.py # Card information APIs
│ ├── card_actions.py # Card action APIs
│ ├── reviewer_control.py # Reviewer control APIs
│ ├── tts_control.py # Text-to-speech APIs
│ ├── ui_control.py # UI control APIs
│ ├── tag_manager.py # Tag management APIs
│ ├── utils.py # Utility functions
│ ├── js/
│ │ └── ankidroid-api.js # JavaScript API implementation
│ ├── manifest.json # Add-on manifest
│ └── config.json # Default configuration
├── tests/ # Unit tests
├── docs/ # Documentation
├── LICENSE # MIT License
├── README.md # This file
├── setup.py # Package setup
└── requirements-dev.txt # Development dependencies
# Install development dependencies
pip install -r requirements-dev.txt
# Run tests
python -m pytest tests/
# Run with coverage
python -m pytest --cov=src/ankidroid_js_api tests/# Build the add-on package
python setup.py build_addon
# The .ankiaddon file will be in the dist/ directoryContributions are welcome! Please feel free to submit a Pull Request.
- Fork the repository
- Create your feature branch (
git checkout -b feature/AmazingFeature) - Commit your changes (
git commit -m 'Add some AmazingFeature') - Push to the branch (
git push origin feature/AmazingFeature) - Open a Pull Request
This project is licensed under the MIT License - see the LICENSE file for details.
This add-on is designed to extend Anki Desktop, which is licensed under the GNU Affero General Public License v3.0 (AGPL-3.0). However, per Anki's plugin policy, add-ons may use any license. This add-on does NOT distribute Anki and must be used with a separately installed copy of Anki Desktop.
For detailed license compliance information, see LICENSE_COMPLIANCE.md and NOTICE.
Runtime Dependencies: None (uses only Python standard library and Anki's built-in APIs)
Development Dependencies: See requirements-dev.txt - MIT, BSD, Apache-2.0 licenses
- AnkiDroid Team - For the original JavaScript API implementation
- Anki Desktop - For the extensible add-on system
If you encounter any issues or have questions:
- Open an issue on GitHub Issues
- Check the documentation
- Join the discussion on Anki Forums
See CHANGELOG.md for version history.