Show and hide the keyboard when navigating to and from the EditFragment

This commit is contained in:
William Brawner 2019-08-04 18:47:23 -07:00 committed by William Brawner
parent 09809cada9
commit feae3be2ec
7 changed files with 93 additions and 40 deletions

View file

@ -29,7 +29,7 @@ android {
exclude 'META-INF/LICENSE'
exclude 'META-INF/DEPENDENCIES'
}
compileSdkVersion 28
compileSdkVersion 29
buildToolsVersion '28.0.3'
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
@ -38,7 +38,7 @@ android {
defaultConfig {
applicationId "com.wbrawner.simplemarkdown"
minSdkVersion 21
targetSdkVersion 28
targetSdkVersion 29
multiDexEnabled true
versionCode 20
versionName "0.7.0"
@ -64,7 +64,6 @@ android {
buildConfigField "boolean", "ENABLE_CUSTOM_CSS", "false"
}
}
flavorDimensions "platform"
dexOptions {
jumboMode true
}
@ -83,11 +82,11 @@ dependencies {
androidTestImplementation('androidx.test.espresso:espresso-core:3.1.0', {
exclude group: 'com.android.support', module: 'support-annotations'
})
androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.1'
androidTestImplementation 'androidx.test:runner:1.1.1'
androidTestImplementation 'androidx.test:rules:1.1.1'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.2.0'
androidTestImplementation 'androidx.test:runner:1.2.0'
androidTestImplementation 'androidx.test:rules:1.2.0'
androidTestImplementation 'androidx.test.uiautomator:uiautomator:2.2.0'
implementation 'androidx.appcompat:appcompat:1.1.0-alpha05'
implementation 'androidx.appcompat:appcompat:1.1.0-rc01'
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
implementation 'com.google.android.material:material:1.0.0'
implementation 'androidx.legacy:legacy-support-v13:1.0.0'
@ -100,9 +99,9 @@ dependencies {
implementation 'com.jakewharton.rxbinding2:rxbinding-design:2.0.0'
implementation 'io.reactivex.rxjava2:rxandroid:2.1.1'
implementation 'io.reactivex.rxjava2:rxjava:2.2.7'
implementation 'com.google.firebase:firebase-core:16.0.9'
implementation 'com.google.firebase:firebase-core:17.0.1'
implementation 'com.android.billingclient:billing:1.2'
implementation 'com.crashlytics.sdk.android:crashlytics:2.10.0'
implementation 'com.crashlytics.sdk.android:crashlytics:2.10.1'
implementation 'androidx.multidex:multidex:2.0.1'
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycle_version"
implementation "androidx.lifecycle:lifecycle-common-java8:$lifecycle_version"

View file

@ -0,0 +1,13 @@
package com.wbrawner.simplemarkdown.utility
import android.content.Context
import android.view.View
import android.view.inputmethod.InputMethodManager
fun View.showKeyboard() =
(context.getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager)
.toggleSoftInput(InputMethodManager.SHOW_FORCED, 0)
fun View.hideKeyboard() =
(context.getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager)
.hideSoftInputFromWindow(windowToken, 0)

View file

@ -0,0 +1,6 @@
package com.wbrawner.simplemarkdown.view
interface ViewPagerPage {
fun onSelected()
fun onDeselected()
}

View file

@ -50,7 +50,9 @@ class MainActivity : AppCompatActivity(), ActivityCompat.OnRequestPermissionsRes
)
}
(application as MarkdownApplication).component.inject(this)
pager.adapter = EditPagerAdapter(supportFragmentManager, this@MainActivity)
val adapter = EditPagerAdapter(supportFragmentManager, this@MainActivity)
pager.adapter = adapter
pager.addOnPageChangeListener(adapter)
pager.pageMargin = 1
pager.setPageMarginDrawable(R.color.colorAccent)
tabLayout.setupWithViewPager(pager)

View file

@ -5,16 +5,21 @@ import android.content.res.Configuration
import androidx.fragment.app.Fragment
import androidx.fragment.app.FragmentManager
import androidx.fragment.app.FragmentPagerAdapter
import androidx.viewpager.widget.ViewPager
import com.wbrawner.simplemarkdown.R
import com.wbrawner.simplemarkdown.view.fragment.EditFragment
import com.wbrawner.simplemarkdown.view.fragment.PreviewFragment
class EditPagerAdapter(fm: FragmentManager, private val context: Context) : FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT) {
class EditPagerAdapter(fm: FragmentManager, private val context: Context)
: FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT), ViewPager.OnPageChangeListener {
private val editFragment = EditFragment()
private val previewFragment = PreviewFragment()
override fun getItem(position: Int): Fragment {
return when (position) {
FRAGMENT_EDIT -> EditFragment()
FRAGMENT_PREVIEW -> PreviewFragment()
FRAGMENT_EDIT -> editFragment
FRAGMENT_PREVIEW -> previewFragment
else -> throw IllegalStateException("Attempting to get fragment for invalid page number")
}
}
@ -40,6 +45,23 @@ class EditPagerAdapter(fm: FragmentManager, private val context: Context) : Frag
}
}
override fun onPageScrollStateChanged(state: Int) {
}
override fun onPageScrolled(position: Int, positionOffset: Float, positionOffsetPixels: Int) {
}
override fun onPageSelected(position: Int) {
when (position) {
FRAGMENT_EDIT -> {
editFragment.onSelected()
}
FRAGMENT_PREVIEW -> {
editFragment.onDeselected()
}
}
}
companion object {
const val FRAGMENT_EDIT = 0
const val FRAGMENT_PREVIEW = 1

View file

@ -1,14 +1,12 @@
package com.wbrawner.simplemarkdown.view.fragment
import android.annotation.SuppressLint
import android.content.Context
import android.os.Bundle
import android.preference.PreferenceManager
import android.view.LayoutInflater
import android.view.MotionEvent
import android.view.View
import android.view.ViewGroup
import android.view.inputmethod.InputMethodManager
import android.widget.EditText
import android.widget.ScrollView
import android.widget.Toast
@ -19,20 +17,22 @@ import com.wbrawner.simplemarkdown.R
import com.wbrawner.simplemarkdown.presentation.MarkdownPresenter
import com.wbrawner.simplemarkdown.utility.MarkdownObserver
import com.wbrawner.simplemarkdown.utility.ReadabilityObserver
import com.wbrawner.simplemarkdown.utility.hideKeyboard
import com.wbrawner.simplemarkdown.utility.showKeyboard
import com.wbrawner.simplemarkdown.view.MarkdownEditView
import com.wbrawner.simplemarkdown.view.ViewPagerPage
import io.reactivex.android.schedulers.AndroidSchedulers
import io.reactivex.schedulers.Schedulers
import java.util.concurrent.TimeUnit
import javax.inject.Inject
import kotlin.math.abs
class EditFragment : Fragment(), MarkdownEditView {
class EditFragment : Fragment(), MarkdownEditView, ViewPagerPage {
@Inject
lateinit var presenter: MarkdownPresenter
private var markdownEditor: EditText? = null
private var markdownEditorScroller: ScrollView? = null
private var lastScrollEvent = -1
@SuppressLint("ClickableViewAccessibility")
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?): View? {
@ -68,19 +68,26 @@ class EditFragment : Fragment(), MarkdownEditView {
super.onViewCreated(view, savedInstanceState)
presenter.setEditView(this@EditFragment)
markdownEditorScroller!!.setOnTouchListener { v, event ->
// The focus should only be set if this was a click, and not a scroll
if (lastScrollEvent == MotionEvent.ACTION_DOWN && event.action == MotionEvent.ACTION_UP) {
if (activity == null) {
return@setOnTouchListener false
var touchDown = 0L
var oldX = 0f
var oldY = 0f
markdownEditorScroller!!.setOnTouchListener { _, event ->
// The ScrollView's onClickListener doesn't seem to be called, so I've had to
// implement a sort of custom click listener that checks that the tap was both quick
// and didn't drag.
when (event?.action) {
MotionEvent.ACTION_DOWN -> {
touchDown = System.currentTimeMillis()
oldX = event.rawX
oldY = event.rawY
}
MotionEvent.ACTION_UP -> {
if (System.currentTimeMillis() - touchDown < 150
&& abs(event.rawX - oldX) < 25
&& abs(event.rawY - oldY) < 25)
markdownEditor?.showKeyboard()
}
val imm = activity
?.getSystemService(Context.INPUT_METHOD_SERVICE) as? InputMethodManager
?: return@setOnTouchListener false
imm.showSoftInput(markdownEditor, InputMethodManager.SHOW_IMPLICIT)
markdownEditor!!.requestFocus()
}
lastScrollEvent = event.action
false
}
}
@ -94,6 +101,15 @@ class EditFragment : Fragment(), MarkdownEditView {
override fun onPause() {
super.onPause()
presenter.setEditView(null)
markdownEditor?.hideKeyboard()
}
override fun onSelected() {
markdownEditor?.showKeyboard()
}
override fun onDeselected() {
markdownEditor?.hideKeyboard()
}
override fun getMarkdown(): String {

View file

@ -29,18 +29,13 @@ class PreviewFragment : Fragment(), MarkdownPreviewView {
inflater: LayoutInflater,
container: ViewGroup?,
savedInstanceState: Bundle?
): View? {
sharedPreferences = PreferenceManager.getDefaultSharedPreferences(container!!.context)
// Inflate the layout for this fragment
val view = inflater.inflate(R.layout.fragment_preview, container, false)
): View? = inflater.inflate(R.layout.fragment_preview, container, false)
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
sharedPreferences = PreferenceManager.getDefaultSharedPreferences(view.context)
markdownPreview = view.findViewById(R.id.markdown_view)
val activity = activity
if (activity != null) {
(activity.application as MarkdownApplication).component.inject(this)
}
if (BuildConfig.DEBUG)
WebView.setWebContentsDebuggingEnabled(true)
return view
(activity?.application as? MarkdownApplication)?.component?.inject(this)
WebView.setWebContentsDebuggingEnabled(BuildConfig.DEBUG)
}
override fun updatePreview(html: String) {