Verified Commit 52cdf794 authored by clairehurst's avatar clairehurst 🌱 Committed by ma1
Browse files

[android] Implement Android-native Connection Assist UI

parent 720195c9
Loading
Loading
Loading
Loading
+1 −0
Changes for mobile/android/fenix/app/src/main/java/org/mozilla/fenix/BrowserDirection.kt: 1 added line, 0 removed lines.
Original line number Diff line number Diff line
@@ -42,4 +42,5 @@ enum class BrowserDirection(@IdRes val fragmentId: Int) {
    FromTranslationsDialogFragment(R.id.translationsDialogFragment),
    FromDownloadLanguagesPreferenceFragment(R.id.downloadLanguagesPreferenceFragment),
    FromMenuDialogFragment(R.id.menuDialogFragment),
    FromTorConnectionAssistFragment(R.id.torConnectionAssistFragment),
}
+70 −3
Changes for mobile/android/fenix/app/src/main/java/org/mozilla/fenix/HomeActivity.kt: 70 added lines, 3 removed lines.
Original line number Diff line number Diff line
@@ -26,6 +26,7 @@ import android.view.MotionEvent
import android.view.View
import android.view.ViewConfiguration
import android.view.WindowManager.LayoutParams.FLAG_SECURE
import androidx.activity.viewModels
import androidx.annotation.CallSuper
import androidx.annotation.IdRes
import androidx.annotation.RequiresApi
@@ -33,7 +34,6 @@ import androidx.annotation.VisibleForTesting
import androidx.appcompat.app.ActionBar
import androidx.appcompat.widget.Toolbar
import androidx.core.splashscreen.SplashScreen.Companion.installSplashScreen
import androidx.core.content.ContentProviderCompat.requireContext
import androidx.lifecycle.lifecycleScope
import androidx.navigation.NavController
import androidx.navigation.fragment.NavHostFragment
@@ -81,6 +81,7 @@ import mozilla.components.support.utils.BrowsersCache
import mozilla.components.support.utils.ManufacturerCodes
import mozilla.components.support.utils.SafeIntent
import mozilla.components.support.utils.TorUtils
import mozilla.components.support.utils.ext.getParcelableExtraCompat
import mozilla.components.support.utils.toSafeIntent
import mozilla.components.support.webextensions.WebExtensionPopupObserver
import mozilla.telemetry.glean.private.NoExtras
@@ -145,11 +146,20 @@ import org.mozilla.fenix.tabhistory.TabHistoryDialogFragment
import org.mozilla.fenix.tabstray.TabsTrayFragment
import org.mozilla.fenix.theme.DefaultThemeManager
import org.mozilla.fenix.theme.ThemeManager
import org.mozilla.fenix.tor.TorConnectionAssistFragmentDirections
import org.mozilla.fenix.tor.TorEvents
import org.mozilla.fenix.utils.Settings
import java.lang.ref.WeakReference
import java.util.Locale

import mozilla.components.browser.engine.gecko.GeckoEngine
import org.mozilla.fenix.components.FenixSnackbar
import org.mozilla.fenix.home.HomeFragment
import org.mozilla.fenix.tor.UrlQuickLoadViewModel
import org.mozilla.geckoview.TorAndroidIntegration
import org.mozilla.geckoview.TorConnectStage
import kotlin.system.exitProcess

/**
 * The main activity of the application. The application is primarily a single Activity (this one)
 * with fragments switching out to display different views. The most important views shown here are the:
@@ -157,7 +167,7 @@ import java.util.Locale
 * - browser screen
 */
@SuppressWarnings("TooManyFunctions", "LargeClass", "LongMethod")
open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity {
open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity, TorAndroidIntegration.BootstrapStateChangeListener {
    private lateinit var binding: ActivityHomeBinding
    lateinit var themeManager: ThemeManager
    lateinit var browsingModeManager: BrowsingModeManager
@@ -229,6 +239,8 @@ open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity {

    private var dialog: RedirectDialogFragment? = null

    private val urlQuickLoadViewModel: UrlQuickLoadViewModel by viewModels()

    @Suppress("ComplexMethod")
    final override fun onCreate(savedInstanceState: Bundle?) {
        // DO NOT MOVE ANYTHING ABOVE THIS getProfilerTime CALL.
@@ -442,6 +454,14 @@ open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity {

        components.notificationsDelegate.bindToActivity(this)

        if (settings().useHtmlConnectionUi) {
            val engine = components.core.engine
            if (engine is GeckoEngine) {
                val torIntegration = engine.getTorIntegrationController()
                torIntegration.registerBootstrapStateChangeListener(this)
            }
        }

        StartupTimeline.onActivityCreateEndHome(this) // DO NOT MOVE ANYTHING BELOW HERE.
    }

@@ -606,8 +626,10 @@ open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity {
    override fun onProvideAssistContent(outContent: AssistContent?) {
        super.onProvideAssistContent(outContent)
        val currentTabUrl = components.core.store.state.selectedTab?.content?.url
        if (components.core.store.state.selectedTab?.content?.private == false) {
            outContent?.webUri = currentTabUrl?.let { Uri.parse(it) }
        }
    }

    @CallSuper
    override fun onDestroy() {
@@ -1080,6 +1102,26 @@ open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity {
        historyMetadata: HistoryMetadataKey? = null,
        additionalHeaders: Map<String, String>? = null,
    ) {
        if (!components.torController.isBootstrapped && !searchTermOrURL.startsWith("about:")) {
            FenixSnackbar.make(
                view = binding.root,
                isDisplayedWithBrowserToolbar = true,
            )
                .setText(getString(R.string.connection_assist_connect_to_tor_before_opening_links))
                .setAction(getString(R.string.connection_assist_connect_to_tor_before_opening_links_confirmation)) {
                    urlQuickLoadViewModel.urlToLoadAfterConnecting.value = searchTermOrURL
                    urlQuickLoadViewModel.maybeBeginBootstrap()
                    if (navHost.navController.previousBackStackEntry?.destination?.id == R.id.torConnectionAssistFragment) {
                        supportFragmentManager.popBackStack()
                    } else {
                        navHost.navController.navigate(
                            TorConnectionAssistFragmentDirections.actionConnectToTorBeforeOpeningLinks()
                        )
                    }
                }
                .show()
            return
        }
        openToBrowser(from, customTabSessionId)
        load(
            searchTermOrURL = searchTermOrURL,
@@ -1219,7 +1261,16 @@ open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity {
        //    return
        //}

        navHost.navController.navigate(NavGraphDirections.actionStartupTorbootstrap())
        if (!settings().useHtmlConnectionUi) {
            navController.navigate(NavGraphDirections.actionStartupTorConnectionAssist())
        } else {
            navController.navigate(NavGraphDirections.actionStartupHome())
            openToBrowserAndLoad(
                searchTermOrURL = "about:torconnect",
                newTab = true,
                from = BrowserDirection.FromHome,
            )
        }
    }

    final override fun attachBaseContext(base: Context) {
@@ -1386,4 +1437,20 @@ open class HomeActivity : LocaleAwareAppCompatActivity(), NavHostActivity {
        // telemetry purposes.
        private const val PWA_RECENTLY_USED_THRESHOLD = DateUtils.DAY_IN_MILLIS * 30L
    }

    fun shutDown() : Nothing {
        finishAndRemoveTask()
        exitProcess(0)
    }

    override fun onBootstrapStateChange(state: String) = Unit
    override fun onBootstrapStageChange(stage: TorConnectStage) = Unit
    override fun onBootstrapProgress(progress: Double, hasWarnings: Boolean) = Unit
    override fun onBootstrapComplete() {
        if (settings().useHtmlConnectionUi) {
            components.useCases.tabsUseCases.removeAllTabs()
            navHost.navController.navigate(NavGraphDirections.actionStartupHome())
        }
    }
    override fun onBootstrapError(code: String?, message: String?, phase: String?, reason: String?) = Unit
}
+19 −0
Changes for mobile/android/fenix/app/src/main/java/org/mozilla/fenix/browser/BaseBrowserFragment.kt: 19 added lines, 0 removed lines.
Original line number Diff line number Diff line
@@ -1549,6 +1549,9 @@ abstract class BaseBrowserFragment :
                val bottomToolbarHeight = context.settings().getBottomToolbarHeight()
                resumeDownloadDialogState(selectedTab.id, context.components.core.store, context, bottomToolbarHeight)
                it.announceForAccessibility(selectedTab.toDisplayTitle())
                if (getCurrentTab()?.content?.url == "about:torconnect") {
                    browserToolbarView.view.visibility = View.GONE
                }
            }
        } else {
            view?.let { view -> initializeUI(view) }
@@ -1573,6 +1576,22 @@ abstract class BaseBrowserFragment :
                    openLinksInExternalApp
                }
            }
        handleBetaHtmlTorConnect()
    }

    private fun handleBetaHtmlTorConnect() {
        val currentTab = getCurrentTab() ?: return
        if (currentTab.content.url == "about:torconnect") {
            if (!requireActivity().settings().useHtmlConnectionUi) {
                requireContext().components.useCases.tabsUseCases.removeTab(currentTab.id)
                (requireActivity() as HomeActivity).navigateToHome(findNavController())
            } else {
                // This just makes it not flash (be visible for a split second) before handleTabSelected() hides it again
                browserToolbarView.view.visibility = View.GONE
            }
        } else if (currentTab.content.url == "about:tor") {
            requireContext().components.useCases.tabsUseCases.removeTab(currentTab.id)
        }
    }

    @CallSuper
+1 −0
Changes for mobile/android/fenix/app/src/main/java/org/mozilla/fenix/components/toolbar/BrowserToolbarMenuController.kt: 1 added line, 0 removed lines.
Original line number Diff line number Diff line
@@ -170,6 +170,7 @@ class DefaultBrowserToolbarMenuController(
                }

                deleteAndQuit(activity, scope, snackbar)
                activity.shutDown()
            }
            is ToolbarMenu.Item.CustomizeReaderView -> {
                readerModeController.showControls()
+4 −0
Changes for mobile/android/fenix/app/src/main/java/org/mozilla/fenix/ext/Activity.kt: 4 added lines, 0 removed lines.
Original line number Diff line number Diff line
@@ -53,6 +53,7 @@ import org.mozilla.fenix.settings.wallpaper.WallpaperSettingsFragmentDirections
import org.mozilla.fenix.share.AddNewDeviceFragmentDirections
import org.mozilla.fenix.shopping.ReviewQualityCheckFragmentDirections
import org.mozilla.fenix.tabstray.TabsTrayFragmentDirections
import org.mozilla.fenix.tor.TorConnectionAssistFragmentDirections
import org.mozilla.fenix.trackingprotection.TrackingProtectionPanelDialogFragmentDirections
import org.mozilla.fenix.translations.TranslationsDialogFragmentDirections
import org.mozilla.fenix.translations.preferences.downloadlanguages.DownloadLanguagesPreferenceFragmentDirections
@@ -330,6 +331,9 @@ private fun getHomeNavDirections(

    BrowserDirection.FromDownloadLanguagesPreferenceFragment ->
        DownloadLanguagesPreferenceFragmentDirections.actionGlobalBrowser()

    BrowserDirection.FromTorConnectionAssistFragment ->
        TorConnectionAssistFragmentDirections.actionGlobalBrowser()
}

const val REQUEST_CODE_BROWSER_ROLE = 1
Loading