Skip to content

Commit

Permalink
Closes mozilla-mobile#1079: Adding find in page feature component.
Browse files Browse the repository at this point in the history
  • Loading branch information
Amejia481 committed Jan 26, 2019
1 parent ab8366e commit 0bd3f0c
Show file tree
Hide file tree
Showing 22 changed files with 924 additions and 12 deletions.
4 changes: 4 additions & 0 deletions .buildconfig.yml
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,10 @@ projects:
path: components/feature/prompts
description: 'Feature that will subscribe to the selected session and will handle all the common prompt dialogs from web content.'
publish: true
feature-findinpage:
path: components/feature/findinpage
description: 'Feature that will subscribe to the selected session and shows a UI based on the data Session.findResults.'
publish: true
browser-awesomebar:
path: components/browser/awesomebar
description: 'A customizable awesomebar component for browsers.'
Expand Down
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,8 @@ _Combined components to implement feature-specific use cases._

* 🔴 [**Prompts**](components/feature/prompts/README.md) - A component that will handle all the common prompt dialogs from web content.

* 🔴 [**Find In Page**](components/feature/findinpage/README.md) - A component that provides an UI widget for [find in page functionality](https://support.mozilla.org/en-US/kb/search-contents-current-page-text-or-links).

## UI

_Generic low-level UI components for building apps._
Expand Down
68 changes: 68 additions & 0 deletions components/feature/findinpage/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
# [Android Components](../../../README.md) > Feature > Prompts

A feature that provides an UI widget for [find in page functionality](https://support.mozilla.org/en-US/kb/search-contents-current-page-text-or-links).

## Usage

### Setting up the dependency
Use Gradle to download the library from [maven.mozilla.org](https://maven.mozilla.org/) ([Setup repository](../../../README.md#maven-repository)):

```Groovy
implementation "org.mozilla.components:feature-findinpage:{latest-version}"
```

### Adding feature find in page.
To use feature find in page you have to do two things:

**1. Add the `FindInPageView` widget to you layout.**

By default, it has a`GONE` visibility, and to make it visible just call `show()`.
```xml
<mozilla.components.feature.findinpage.FindInPageView
android:id="@+id/find_in_page"
android:layout_width="match_parent"
android:background="#FFFFFFFF"
android:elevation="10dp"
android:layout_height="56dp"
android:padding="4dp" />
```

These are the properties that you can customize of this widget.
```xml
<attr name="findInPageQueryTextColor" format="reference|color"/>
<attr name="findInPageQueryHintTextColor" format="reference|color"/>
<attr name="findInPageQueryTextSize" format="dimension"/>
<attr name="findInPageResultCountTextColor" format="reference|color"/>
<attr name="findInPageResultCountTextSize" format="dimension"/>
<attr name="findInPageButtonsTint" format="reference|color"/>
```

**2. Start the `FindInPageFeature` in you activity/fragment.**

```kotlin
val findInPageView = layout.findViewById<FindInPageView>(R.id.find_in_page)

val findInPageFeature = FindInPageFeature(
sessionManager = sessionManager,
findInPageView = findInPageView
)

lifecycle.addObservers( findInPageFeature)

// To make it visible
findInPageView.show()

// Optional
findInPageView.onCloseButtonPressListener = {
// Do something.
}

```

🦊 A practical example of using feature find in page can be found in [Sample Browser](https://github.com/mozilla-mobile/android-components/tree/master/samples/browser).

## License

This Source Code Form is subject to the terms of the Mozilla Public
License, v. 2.0. If a copy of the MPL was not distributed with this
file, You can obtain one at http://mozilla.org/MPL/2.0/
41 changes: 41 additions & 0 deletions components/feature/findinpage/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */

apply plugin: 'com.android.library'
apply plugin: 'kotlin-android'

android {
compileSdkVersion config.compileSdkVersion

defaultConfig {
minSdkVersion config.minSdkVersion
targetSdkVersion config.targetSdkVersion
}

buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}

dependencies {
implementation project(':browser-session')
implementation project(':concept-engine')
implementation project(':support-ktx')
implementation project(':ui-icons')

implementation Dependencies.kotlin_stdlib
implementation Dependencies.support_constraintlayout

testImplementation Dependencies.androidx_test_core
testImplementation Dependencies.testing_junit
testImplementation Dependencies.testing_robolectric
testImplementation Dependencies.testing_mockito
testImplementation project(':support-test')
}

apply from: '../../../publish.gradle'
ext.configurePublish(config.componentsGroupId, archivesBaseName, project.ext.description)
21 changes: 21 additions & 0 deletions components/feature/findinpage/proguard-rules.pro
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Add project specific ProGuard rules here.
# You can control the set of applied configuration files using the
# proguardFiles setting in build.gradle.
#
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html

# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}

# Uncomment this to preserve the line number information for
# debugging stack traces.
#-keepattributes SourceFile,LineNumberTable

# If you keep the line number information, uncomment this to
# hide the original source file name.
#-renamesourcefileattribute SourceFile
5 changes: 5 additions & 0 deletions components/feature/findinpage/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<!-- This Source Code Form is subject to the terms of the Mozilla Public
- License, v. 2.0. If a copy of the MPL was not distributed with this
- file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="mozilla.components.feature.findinpage" />
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */

package mozilla.components.feature.findinpage

import android.support.annotation.CallSuper
import android.support.annotation.VisibleForTesting
import android.support.annotation.VisibleForTesting.PRIVATE
import mozilla.components.browser.session.SelectionAwareSessionObserver
import mozilla.components.browser.session.Session
import mozilla.components.browser.session.SessionManager
import mozilla.components.support.base.feature.LifecycleAwareFeature

/**
* This feature will subscribe to the currently selected [Session] and when started will forward
* [Session.Observer.onFindResult] calls to the [findInPageView] ui widget.
*
* @property sessionManager The [SessionManager] instance in order to subscribe to the selected [Session].
* @property findInPageView The [FindInPageView] instance that will capture user interactions, and new calls
* of [Session.Observer.onFindResult] will be delegated.
*/

class FindInPageFeature(
private val sessionManager: SessionManager,
private val findInPageView: FindInPageView
) : LifecycleAwareFeature {

private val observer = FindInPageRequestObserver(sessionManager, feature = this)

/**
* Start observing the selected session and forwarding events to the [findInPageView] widget.
*/
override fun start() {
observer.observeSelected()
val selectedSession = sessionManager.selectedSession ?: return
val engineSession = sessionManager.getEngineSession(selectedSession) ?: return
findInPageView.sessionEngine = engineSession
}

/**
* Stop observing the selected session and forwarding events to the [findInPageView] widget.
*/
override fun stop() {
observer.stop()
}

/**
* Informs the [findInPageView] widget that the back button has been pressed.
*
* @return true if the event was handled, otherwise false.
*/
fun onBackPressed(): Boolean {
return if (findInPageView.isActive()) {
findInPageView.onCloseButtonClicked()
true
} else {
false
}
}

@VisibleForTesting(otherwise = PRIVATE)
internal fun onFindResult(session: Session, result: Session.FindResult) {
findInPageView.onFindResultReceived(result)
}

internal class FindInPageRequestObserver(
private val sessionManager: SessionManager,
private val feature: FindInPageFeature
) : SelectionAwareSessionObserver(sessionManager) {

override fun onFindResult(session: Session, result: Session.FindResult) {
feature.onFindResult(session, result)
}

@CallSuper
override fun onSessionSelected(session: Session) {
super.onSessionSelected(session)
val engineSession = sessionManager.getEngineSession(session) ?: return
feature.findInPageView.sessionEngine = engineSession
}
}
}

0 comments on commit 0bd3f0c

Please sign in to comment.