Skip to content

Merge upstream AnkiDroid - #27

Merged
float3 merged 50 commits into
ankiquestfrom
main
Sep 27, 2026
Merged

float3 merged 50 commits into
ankiquestfrom
main

Conversation

@float3

@float3 float3 commented Sep 25, 2026

Copy link
Copy Markdown
Owner

27 new commits from ankidroid/Anki-Android main.

Merge with a merge commit, never squash or rebase, so ankiquest keeps upstream's history.

If this conflicts, merge main into a branch from ankiquest, resolve there, and merge that branch instead. Never commit to main: it mirrors upstream.

Reject truncated bodies instead of forwarding zero-padded protobuf messages.

HTTPD handles body-read failures so it can close the connection.

Assisted-by: GPT-6
Rebuilding the fragment can cause an ANR

This adds a fast path when the fragment does not need to be
rebuilt.

Part of 19737

Assisted-by: Claude Fable 5

� Conflicts:
�	AnkiDroid/src/main/java/com/ichi2/anki/CardBrowser.kt
Fixes 18618

Assisted-by: Claude Opus 4.7 - all
Assisted-by: GPT-6 - screenshot test
android:textColorHint was #79747E. On #E4F5FD this led to a contrast of 4.07:1

#716C76 is 4.57:1 - acceptable for text

Assisted-by: Claude Opus 4.7 - color
.click() opened "Create subdeck"

customizeReminderBeforeCreatingIt
editReminderChangingDeckAndSettings

Fixes 22040

Assisted-by: GPT-6
Dependabot cannot obtain release dates for older AndroidX versions from
Google Maven.

Existing updates are then closed as `update_no_longer_possible` if recreated.

See PRs 21219 21314 & 21552

https://redirect.github.com/dependabot/dependabot-core/issues/16055

Part of 22028
Concurrent events could flip the reviewer back to the question.

This caused an issue in emulator testing.

Fixes 22041

Assisted-by: GPT-6
Allow unit test JVMs to access JDK internals.

----

See https://robolectric.org/getting-started/#running-with-java-17-and-higher

> When running tests on Java 17 or higher, the JVM requires ``--add-opens` flags
> so that Robolectric can access internal OpenJDK classes and APIs
> (`java.lang`, `java.io`, `jdk.internal.access`, etc.). Add the following
> `jvmArgs to your unit test configuration in `build.gradle` / `build.gradle.kts`:

```kt
android {
  testOptions {
    unitTests.all {
      it.jvmArgs(
        "--add-opens=java.base/java.lang=ALL-UNNAMED",
        "--add-opens=java.base/java.util=ALL-UNNAMED",
        "--add-opens=java.base/java.io=ALL-UNNAMED",
        "--add-opens=java.base/java.net=ALL-UNNAMED",
        "--add-opens=java.base/java.security=ALL-UNNAMED",
        "--add-opens=java.base/java.text=ALL-UNNAMED",
        "--add-opens=java.base/jdk.internal.access=ALL-UNNAMED",
        "--add-opens=java.desktop/java.awt.font=ALL-UNNAMED",
        "--add-opens=jdk.compiler/com.sun.tools.javac.api=ALL-UNNAMED",
      )
    }
  }
}
```

Assisted-by: GPT-6
Prep for 22042

Assisted-by: GPT-6
Note: This fix is unverified, I was unable to produce
 the underlying error.
Fixing the underlying error could cause this code to be removed.

* Preserve stdout and command exit status
* Only retry on offline connection errors

Logcat is kept outside the helper so stderr remains usable

Fixes 22042

Assisted-by: GPT-6
This caused test failures trying to access a disposed backend

Fixes DeckPickerTest.checkIfClickOnCountsLayoutOpensStudyOptionsOnMobile

Fixes 22044

Assisted-by: GPT-6
Wait for WebView.canZoomIn before requesting a zoom.

Using the DOM wasn't sufficient

This fixes emulator tests:
- buryingQuestionResetsZoomAndStartsNextQuestionAtTop
- showingAnswerResetsZoomAndPreservesScrollPosition
- answerAnchorTakesPrecedenceAfterResettingZoom
- answerRenderingWaitsForZoomReset
- nextQuestionResetsZoomAndStartsAtTop

Fixes 22043

Assisted-by: GPT-6
Both `push` and `pull_request` triggered the same workflows.

Drop `push` workflows for dependabot branches.

Fixes 22063

Assisted-by: GPT-6
Reload only after the optimization completes so the page picks up saved limits and optimized parameters.

Normal saves still close the screen.

This is prep for Anki 26.08/09

Part of 21926
See https://redirect.github.com/ankitects/anki/pull/4981
See https://redirect.github.com/ankitects/anki/issues/4978

Assisted-by: GPT-6
Required for androidxCoreKtx:1.19.1 (androidx.core)

Assisted-by: GPT-6
Already assigned above

Assisted-by: GPT-6
Call `.mutate()` so the state of other icons is unchanged.

Fixes 22067

Assisted-by: GPT-6
As a step, rather than needing to download the artifacts

* Tests with assumption failures appear, but last, and hidden
* Same with ignored tests

Assisted-by: GPT-6
This is used by `PermissionsTest`, so it caused a runtime fetch.

Related to 22069

Assisted-by: GPT-6
097c7cd` moved `CollectionManager` down, so these methods can now be
moved to `:anki-common`.

More work for the for `:widgets` multimodule migration

Part of 20737

Assisted-by: Claude Fable 5
Part of 20737

Assisted-by: Claude Fable 5
Part of 20737

Assisted-by: Claude Fable 5
TestChangeSubscriber moves to testFixtures, and ChangeManagerTest
uses its ChangeCounter directly

Part of 20737

Assisted-by: Claude Fable 5
For the widget feature module extraction

Part of 20737

Assisted-by: Claude Opus 4.8
(cherry picked from commit 28885ffe7d677a28397b5ffddc32561d29ce4cca)
@github-actions

github-actions Bot commented Sep 25, 2026 •

Copy link
Copy Markdown

Snapshot diff report vs ankiquest. Open screenshot-diff for diffs.

  • BrowserColumnSelectionFragmentScreenshotTest: 8 changes
  • BrowserOptionsDialogScreenshotTest: 2 changes
  • CardBrowserScreenshotTest: 1 change
  • DeckPickerScreenshotTest: 7 changes
  • NavigationDrawerScreenshotTest: 1 change
  • PreferencesScreenshotTest: 3 changes
  • ReviewRemindersScreenshotTest: 7 changes
All 29 changed screenshots

BrowserColumnSelectionFragmentScreenshotTest

  • gesture_navigation_compare.png
  • gesture_navigation_scrolled_to_bottom_compare.png
  • landscape_compare.png
  • landscape_scrolled_to_bottom_compare.png
  • portrait_compare.png
  • portrait_cutout_compare.png
  • portrait_cutout_scrolled_to_bottom_compare.png
  • portrait_scrolled_to_bottom_compare.png

BrowserOptionsDialogScreenshotTest

  • default_search_empty_compare.png
  • default_search_populated_compare.png

CardBrowserScreenshotTest

  • keyboard_scrolled_to_bottom_compare.png

DeckPickerScreenshotTest

  • deck_list_after_dismissing_create_deck_dialog_compare.png
  • hierarchy_lines_collapsed_compare.png
  • hierarchy_lines_compare.png
  • hierarchy_lines_deep_nesting_compare.png
  • hierarchy_lines_many_siblings_compare.png
  • keyboard_open_scrolled_to_bottom_compare.png
  • keyboard_studied_line_overlaying_deck_name_compare.png

NavigationDrawerScreenshotTest

  • navigationDrawer_compare.png

PreferencesScreenshotTest

  • HeaderFragment_compare.png
  • HeaderFragment_landscape_compare.png
  • HeaderFragment_portrait_compare.png

ReviewRemindersScreenshotTest

  • settingsHostTablet_scheduleReminders_compare.png
  • settingsHostTablet_troubleshooting_compare.png
  • studyOptionsFragmentHost_scheduleReminders_compare.png
  • studyOptionsFragmentHost_systemBars_compare.png
  • studyOptionsFragmentHost_systemBars_scrolledToEnd_compare.png
  • studyOptionsFragmentHost_troubleshooting_compare.png
  • studyOptionsFragmentHost_troubleshooting_systemBars_compare.png

update capitalizePy() to solve theoretical issue ß
lukstbit and others added 22 commits September 25, 2026 19:18
This overrides the default behavior of AppBarLayout which uses
colorSurfaceContainer when scrolling the content.

With colorSurface the colors remains constant when scrolling as well as
in relation to the status bar color.

See https://github.com/material-components/material-components-android/blob/master/docs/components/TopAppBar.md#scrolling-behavior-attributes
Camera option in IO and multimedia are now hidden when nothing can handle IMAGE_CAPTURE. The query is
declared in our own manifest, since until now it only reached the merged
manifest through the image cropper library.
After preset optimization, wait for `updateDeckConfigs` before reloading.

Reloading from the HTTP handler could abort `fetch` and show an
 error dialog that blocked the page.

Fixes 22072

Assisted-by: GPT-6
Following Brayan's PR, I grepped for my name and removed
84 references

AnkiDroid is standardizing licenses to SPDX.

I removed my copyright lines from the files as-per
docs/contributing/copyright-headers.md

Issue 20954

This change was not performed using LLMs and I have verified that it is
correct
The "cards shown" subtitle went blank after a rotation. The browser now
keeps its last search result, so the count comes straight back.
Part of 20497

Assisted-by: GPT-6 (with lots of rounds of feedback)

Co-authored-by: Ashish Yadav <48384865+criticalAY@users.noreply.github.com>
Part of 20497

Assisted-by: GPT-6 (with lots of rounds of feedback)
There is a dependency on `:compat`, so this can't go lower

Prep for moving AnkiActivity down the dependency tree

Part of 20737

Assisted-by: GPT-6
Per discussion with Brayan and David, we're planning to deprecate the ETA functionality in AnkiDroid. It will be an add-on instead, as the calculation is not accurate. It will be easier to remove later if we do not add it to review reminders.
To prevent someone from adding swear words in and making it look like it's app-issued text.
The notification body read "1 cards due" for a single card.

Assisted-by: Claude Opus 5
These are now translated, so the _do_not_translate suffix is dropped.
The notification channel ID is unchanged; only its display name is,
which is now sentence case.

Assisted-by: Claude Opus 5
The toolbar title and the time button's text are both set at runtime,
so their placeholders become tools: attributes rather than resources.

Assisted-by: Claude Opus 5
Enabled/Disabled reuse the generic strings. A translator comment alongside
full_screen_off is added to keep DuplicateCrowdInStrings quiet.

Assisted-by: Claude Opus 5
As pointed out by David, a creative deck name like `French\u202B\u200E, you silly person` would result in an outputted notification title of `It's time to study "French", you silly person`, breaching quotation mark containment.

This is essentially the inverse of `Lang.kt`'s `withoutUnicodeIsolation`, but could not be put into `Lang.kt` due to that being in `libanki`.

Assisted-by: Claude Opus 5.5
@float3
float3 merged commit b2a8821 into ankiquest Sep 27, 2026
34 checks passed
@float3
float3 deleted the main branch September 27, 2026 11:42
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants