Merge branch 'dev' of gitlab.com:stax-river/poker-analytics into dev

feature/top10
Laurent 7 years ago
commit a24106a60a
  1. 10
      app/src/main/AndroidManifest.xml
  2. 17
      app/src/main/java/net/pokeranalytics/android/model/filter/QueryCondition.kt
  3. 6
      app/src/main/java/net/pokeranalytics/android/model/realm/Filter.kt
  4. 37
      app/src/main/java/net/pokeranalytics/android/ui/extensions/UIExtensions.kt
  5. 4
      app/src/main/java/net/pokeranalytics/android/ui/fragment/CalendarFragment.kt
  6. 15
      app/src/main/java/net/pokeranalytics/android/ui/fragment/FilterDetailsFragment.kt
  7. 1
      app/src/main/java/net/pokeranalytics/android/ui/fragment/ReportsFragment.kt
  8. 5
      app/src/main/java/net/pokeranalytics/android/ui/fragment/SessionFragment.kt
  9. 10
      app/src/main/java/net/pokeranalytics/android/ui/fragment/SettingsFragment.kt
  10. 39
      app/src/main/res/layout/fragment_loader.xml
  11. 6
      app/src/main/res/xml/provider_paths.xml

@ -98,6 +98,16 @@
android:name="preloaded_fonts" android:name="preloaded_fonts"
android:resource="@array/preloaded_fonts" /> android:resource="@array/preloaded_fonts" />
<provider
android:name="androidx.core.content.FileProvider"
android:authorities="${applicationId}.fileprovider"
android:grantUriPermissions="true"
android:exported="false">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths" />
</provider>
</application> </application>
</manifest> </manifest>

@ -17,11 +17,12 @@ import net.pokeranalytics.android.ui.view.rowrepresentable.FilterSectionRow
import net.pokeranalytics.android.ui.view.rowrepresentable.FilterElementRow import net.pokeranalytics.android.ui.view.rowrepresentable.FilterElementRow
import net.pokeranalytics.android.util.extensions.endOfDay import net.pokeranalytics.android.util.extensions.endOfDay
import net.pokeranalytics.android.util.extensions.startOfDay import net.pokeranalytics.android.util.extensions.startOfDay
import java.text.DateFormatSymbols
import java.util.* import java.util.*
import kotlin.collections.ArrayList import kotlin.collections.ArrayList
fun List<QueryCondition>.name() : String { fun List<QueryCondition>.name() : String {
return this.map { it.id }.joinToString(" / ") return this.map { it.label() }.joinToString(" / ")
} }
//inline fun <reified T : Filterable> List<QueryCondition>.query(realm: Realm): RealmQuery<T> { //inline fun <reified T : Filterable> List<QueryCondition>.query(realm: Realm): RealmQuery<T> {
@ -43,7 +44,11 @@ inline fun <reified T : Filterable> List<QueryCondition>.queryWith(query: RealmQ
* A new type should also set the expected numericValues required in the [filterValuesExpectedKeys] * A new type should also set the expected numericValues required in the [filterValuesExpectedKeys]
*/ */
sealed class QueryCondition : FilterElementRow { interface Labelable {
fun label() : String
}
sealed class QueryCondition : FilterElementRow, Labelable {
interface Valuable <T : ArrayList<T>> { interface Valuable <T : ArrayList<T>> {
var values: ArrayList<T>? var values: ArrayList<T>?
@ -107,6 +112,14 @@ sealed class QueryCondition : FilterElementRow {
} }
} }
override fun label(): String {
return when (this) {
is YEAR -> "$intValue"
is MONTH -> DateFormatSymbols.getInstance(Locale.getDefault()).months[intValue]
else -> baseId
}
}
override var filterSectionRow: FilterSectionRow = FilterSectionRow.CASH_TOURNAMENT override var filterSectionRow: FilterSectionRow = FilterSectionRow.CASH_TOURNAMENT
open class OperationQueryCondition : QueryCondition(), asDoubleValue { open class OperationQueryCondition : QueryCondition(), asDoubleValue {

@ -93,6 +93,12 @@ open class Filter : RealmObject() {
} }
} }
fun remove(filterCategoryRow: FilterCategoryRow) {
val sections = filterCategoryRow.filterSectionRows.map { it.name }
val savedSections = filterConditions.filter { sections.contains(it.sectionName) }
this.filterConditions.removeAll(savedSections)
}
fun countBy(filterCategoryRow: FilterCategoryRow): Int { fun countBy(filterCategoryRow: FilterCategoryRow): Int {
val sections = filterCategoryRow.filterSectionRows.map { it.name } val sections = filterCategoryRow.filterSectionRows.map { it.name }
println("list of sections $sections") println("list of sections $sections")

@ -11,6 +11,7 @@ import androidx.appcompat.app.AlertDialog
import androidx.appcompat.widget.AppCompatTextView import androidx.appcompat.widget.AppCompatTextView
import androidx.browser.customtabs.CustomTabsIntent import androidx.browser.customtabs.CustomTabsIntent
import androidx.core.content.ContextCompat import androidx.core.content.ContextCompat
import androidx.core.content.FileProvider
import androidx.core.view.isVisible import androidx.core.view.isVisible
import net.pokeranalytics.android.BuildConfig import net.pokeranalytics.android.BuildConfig
import net.pokeranalytics.android.R import net.pokeranalytics.android.R
@ -19,6 +20,11 @@ import net.pokeranalytics.android.ui.activity.components.PokerAnalyticsActivity
import net.pokeranalytics.android.ui.fragment.components.PokerAnalyticsFragment import net.pokeranalytics.android.ui.fragment.components.PokerAnalyticsFragment
import net.pokeranalytics.android.util.DeviceUtils import net.pokeranalytics.android.util.DeviceUtils
import net.pokeranalytics.android.util.URL import net.pokeranalytics.android.util.URL
import java.io.File
// Sizes // Sizes
@ -63,20 +69,33 @@ fun PokerAnalyticsActivity.openPlayStorePage() {
} }
// Open email for "Contact us" // Open email for "Contact us"
fun PokerAnalyticsActivity.openContactMail(subjectStringRes: Int) { fun PokerAnalyticsActivity.openContactMail(subjectStringRes: Int, filePath: String?= null) {
val info = "v${BuildConfig.VERSION_NAME}(${BuildConfig.VERSION_CODE}), Android ${android.os.Build.VERSION.SDK_INT}, ${DeviceUtils.getDeviceName()}" val info = "v${BuildConfig.VERSION_NAME}(${BuildConfig.VERSION_CODE}), Android ${android.os.Build.VERSION.SDK_INT}, ${DeviceUtils.getDeviceName()}"
val intent = Intent(Intent.ACTION_SENDTO)
intent.data = Uri.parse("mailto:${URL.SUPPORT_EMAIL.value}") val emailIntent = Intent(Intent.ACTION_SEND)
intent.putExtra(Intent.EXTRA_SUBJECT, getString(subjectStringRes))
intent.putExtra(Intent.EXTRA_EMAIL, URL.SUPPORT_EMAIL.value) filePath?.let {
intent.putExtra(Intent.EXTRA_TEXT, "\n\n$info") val databaseFile = File(it)
startActivity(Intent.createChooser(intent, getString(R.string.contact))) val contentUri = FileProvider.getUriForFile(this, "net.pokeranalytics.android.fileprovider", databaseFile)
if (contentUri != null) {
emailIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
emailIntent.setDataAndType(contentUri, contentResolver.getType(contentUri))
emailIntent.putExtra(Intent.EXTRA_STREAM, contentUri)
}
}
emailIntent.type = "message/rfc822"
emailIntent.putExtra(Intent.EXTRA_SUBJECT, getString(subjectStringRes))
emailIntent.putExtra(Intent.EXTRA_TEXT, "\n\n$info")
emailIntent.putExtra(Intent.EXTRA_EMAIL, arrayOf(URL.SUPPORT_EMAIL.value))
startActivity(Intent.createChooser(emailIntent, getString(R.string.contact)))
} }
// Open custom tab // Open custom tab
fun PokerAnalyticsActivity.openUrl(url: String) { fun PokerAnalyticsActivity.openUrl(url: String) {
val builder: CustomTabsIntent.Builder = CustomTabsIntent.Builder() val builder: CustomTabsIntent.Builder = CustomTabsIntent.Builder()
builder.setToolbarColor(ContextCompat.getColor(this, R.color.colorPrimary)) builder.setToolbarColor(ContextCompat.getColor(this, net.pokeranalytics.android.R.color.colorPrimary))
val customTabsIntent = builder.build() val customTabsIntent = builder.build()
customTabsIntent.launchUrl(this, Uri.parse(url)) customTabsIntent.launchUrl(this, Uri.parse(url))
} }
@ -102,7 +121,7 @@ fun showAlertDialog(context: Context, title: Int? = null, message: Int? = null)
message?.let { message?.let {
builder.setMessage(message) builder.setMessage(message)
} }
builder.setPositiveButton(R.string.ok, null) builder.setPositiveButton(net.pokeranalytics.android.R.string.ok, null)
builder.show() builder.show()
} }

@ -240,6 +240,8 @@ class CalendarFragment : SessionObserverFragment(), CoroutineScope, StaticRowRep
// Compute data per YEAR and MONTH // Compute data per YEAR and MONTH
println(">>>> ${Comparator.MONTH_OF_YEAR.queryConditions.map { it.id }}")
val monthConditions = when (sessionTypeCondition) { val monthConditions = when (sessionTypeCondition) {
QueryCondition.CASH -> listOf(Comparator.YEAR, Comparator.MONTH_OF_YEAR, Comparator.CASH).combined() QueryCondition.CASH -> listOf(Comparator.YEAR, Comparator.MONTH_OF_YEAR, Comparator.CASH).combined()
QueryCondition.TOURNAMENT -> listOf(Comparator.YEAR, Comparator.MONTH_OF_YEAR, Comparator.TOURNAMENT).combined() QueryCondition.TOURNAMENT -> listOf(Comparator.YEAR, Comparator.MONTH_OF_YEAR, Comparator.TOURNAMENT).combined()
@ -255,7 +257,7 @@ class CalendarFragment : SessionObserverFragment(), CoroutineScope, StaticRowRep
conditions.forEach { condition -> conditions.forEach { condition ->
when (condition) { when (condition) {
is QueryCondition.YEAR -> calendar.set(Calendar.YEAR, condition.intValue) is QueryCondition.YEAR -> calendar.set(Calendar.YEAR, condition.intValue)
is QueryCondition.MONTH -> calendar.set(Calendar.YEAR, condition.intValue) is QueryCondition.MONTH -> calendar.set(Calendar.MONTH, condition.intValue)
} }
} }

@ -38,14 +38,14 @@ open class FilterDetailsFragment : PokerAnalyticsFragment(), StaticRowRepresent
lateinit var parentActivity: PokerAnalyticsActivity lateinit var parentActivity: PokerAnalyticsActivity
lateinit var rowRepresentableAdapter: RowRepresentableAdapter lateinit var rowRepresentableAdapter: RowRepresentableAdapter
private lateinit var primaryKey: String
private lateinit var filterCategoryRow: FilterCategoryRow
private var currentFilter: Filter? = null private var currentFilter: Filter? = null
private var rows: ArrayList<RowRepresentable> = ArrayList() private var rows: ArrayList<RowRepresentable> = ArrayList()
private var rowsForFilterSubcategoryRow: HashMap<FilterSectionRow, ArrayList<RowRepresentable>> = HashMap() private var rowsForFilterSubcategoryRow: HashMap<FilterSectionRow, ArrayList<RowRepresentable>> = HashMap()
private var primaryKey: String? = null
private var filterMenu: Menu? = null private var filterMenu: Menu? = null
private var filterCategoryRow: FilterCategoryRow? = null
private val selectedRows = ArrayList<QueryCondition>() private val selectedRows = ArrayList<QueryCondition>()
private var isUpdating = false private var isUpdating = false
private var shouldOpenKeyboard = true private var shouldOpenKeyboard = true
@ -174,17 +174,14 @@ open class FilterDetailsFragment : PokerAnalyticsFragment(), StaticRowRepresent
*/ */
private fun initData() { private fun initData() {
primaryKey?.let { currentFilter = Filter.getFilterBydId(getRealm(), primaryKey)
currentFilter = Filter.getFilterBydId(getRealm(), it)
}
filterCategoryRow?.let {
this.appBar.toolbar.title = it.localizedTitle(requireContext()) this.appBar.toolbar.title = filterCategoryRow.localizedTitle(requireContext())
this.rows.clear() this.rows.clear()
this.rowsForFilterSubcategoryRow.clear() this.rowsForFilterSubcategoryRow.clear()
this.rows.addAll(it.filterElements) this.rows.addAll(filterCategoryRow.filterElements)
this.rows.forEach { element -> this.rows.forEach { element ->
if (element is QueryCondition && currentFilter?.contains(element) == true) { if (element is QueryCondition && currentFilter?.contains(element) == true) {
@ -195,7 +192,6 @@ open class FilterDetailsFragment : PokerAnalyticsFragment(), StaticRowRepresent
this.rowRepresentableAdapter = RowRepresentableAdapter(this, this) this.rowRepresentableAdapter = RowRepresentableAdapter(this, this)
this.recyclerView.adapter = rowRepresentableAdapter this.recyclerView.adapter = rowRepresentableAdapter
}
} }
/** /**
@ -238,6 +234,7 @@ open class FilterDetailsFragment : PokerAnalyticsFragment(), StaticRowRepresent
val realm = getRealm() val realm = getRealm()
realm.beginTransaction() realm.beginTransaction()
currentFilter?.remove(filterCategoryRow)
currentFilter?.createOrUpdateFilterConditions(selectedRows) currentFilter?.createOrUpdateFilterConditions(selectedRows)
realm.commitTransaction() realm.commitTransaction()

@ -18,7 +18,6 @@ import net.pokeranalytics.android.ui.activity.ReportDetailsActivity
import net.pokeranalytics.android.ui.adapter.RowRepresentableAdapter import net.pokeranalytics.android.ui.adapter.RowRepresentableAdapter
import net.pokeranalytics.android.ui.adapter.RowRepresentableDelegate import net.pokeranalytics.android.ui.adapter.RowRepresentableDelegate
import net.pokeranalytics.android.ui.adapter.StaticRowRepresentableDataSource import net.pokeranalytics.android.ui.adapter.StaticRowRepresentableDataSource
import net.pokeranalytics.android.ui.fragment.components.LoaderDialogFragment
import net.pokeranalytics.android.ui.fragment.components.PokerAnalyticsFragment import net.pokeranalytics.android.ui.fragment.components.PokerAnalyticsFragment
import net.pokeranalytics.android.ui.view.RowRepresentable import net.pokeranalytics.android.ui.view.RowRepresentable
import net.pokeranalytics.android.ui.view.rowrepresentable.ReportRow import net.pokeranalytics.android.ui.view.rowrepresentable.ReportRow

@ -43,8 +43,9 @@ class SessionFragment : PokerAnalyticsFragment(), RowRepresentableDelegate {
private val refreshTimer: Runnable = object : Runnable { private val refreshTimer: Runnable = object : Runnable {
override fun run() { override fun run() {
// Refresh header each 30 seconds // Refresh header each 30 seconds
currentSession.updateRowRepresentation()
sessionAdapter.notifyItemChanged(0) sessionAdapter.notifyItemChanged(0)
handler.postDelayed(this, 30000) handler.postDelayed(this, 60000)
} }
} }
@ -181,7 +182,7 @@ class SessionFragment : PokerAnalyticsFragment(), RowRepresentableDelegate {
floatingActionButton.animate().scaleX(1f).scaleY(1f).alpha(1f) floatingActionButton.animate().scaleX(1f).scaleY(1f).alpha(1f)
.setDuration(animationDuration) .setDuration(animationDuration)
.setInterpolator(OvershootInterpolator()).start() .setInterpolator(OvershootInterpolator()).start()
handler.postDelayed(refreshTimer, 30000) handler.postDelayed(refreshTimer, 60000)
} }
SessionState.PAUSED -> { SessionState.PAUSED -> {
sessionMenu?.findItem(R.id.restart)?.isVisible = true sessionMenu?.findItem(R.id.restart)?.isVisible = true

@ -11,7 +11,6 @@ import io.realm.Realm
import kotlinx.android.synthetic.main.fragment_settings.* import kotlinx.android.synthetic.main.fragment_settings.*
import net.pokeranalytics.android.BuildConfig import net.pokeranalytics.android.BuildConfig
import net.pokeranalytics.android.R import net.pokeranalytics.android.R
import net.pokeranalytics.android.model.realm.Bankroll
import net.pokeranalytics.android.model.realm.Session import net.pokeranalytics.android.model.realm.Session
import net.pokeranalytics.android.ui.activity.CurrenciesActivity import net.pokeranalytics.android.ui.activity.CurrenciesActivity
import net.pokeranalytics.android.ui.activity.DataListActivity import net.pokeranalytics.android.ui.activity.DataListActivity
@ -20,15 +19,15 @@ import net.pokeranalytics.android.ui.activity.components.PokerAnalyticsActivity
import net.pokeranalytics.android.ui.adapter.RowRepresentableAdapter import net.pokeranalytics.android.ui.adapter.RowRepresentableAdapter
import net.pokeranalytics.android.ui.adapter.RowRepresentableDelegate import net.pokeranalytics.android.ui.adapter.RowRepresentableDelegate
import net.pokeranalytics.android.ui.adapter.StaticRowRepresentableDataSource import net.pokeranalytics.android.ui.adapter.StaticRowRepresentableDataSource
import net.pokeranalytics.android.ui.extensions.openContactMail
import net.pokeranalytics.android.ui.extensions.openPlayStorePage
import net.pokeranalytics.android.ui.extensions.openUrl
import net.pokeranalytics.android.ui.fragment.components.PokerAnalyticsFragment import net.pokeranalytics.android.ui.fragment.components.PokerAnalyticsFragment
import net.pokeranalytics.android.ui.view.RowRepresentable import net.pokeranalytics.android.ui.view.RowRepresentable
import net.pokeranalytics.android.ui.view.rowrepresentable.SettingRow import net.pokeranalytics.android.ui.view.rowrepresentable.SettingRow
import net.pokeranalytics.android.util.Preferences import net.pokeranalytics.android.util.Preferences
import net.pokeranalytics.android.util.URL import net.pokeranalytics.android.util.URL
import net.pokeranalytics.android.util.UserDefaults import net.pokeranalytics.android.util.UserDefaults
import net.pokeranalytics.android.ui.extensions.openContactMail
import net.pokeranalytics.android.ui.extensions.openPlayStorePage
import net.pokeranalytics.android.ui.extensions.openUrl
import java.util.* import java.util.*
@ -98,11 +97,10 @@ class SettingsFragment : PokerAnalyticsFragment(), RowRepresentableDelegate, Sta
} }
override fun onRowSelected(position: Int, row: RowRepresentable, fromAction: Boolean) { override fun onRowSelected(position: Int, row: RowRepresentable, fromAction: Boolean) {
when (row) { when (row) {
SettingRow.RATE_APP -> parentActivity.openPlayStorePage() SettingRow.RATE_APP -> parentActivity.openPlayStorePage()
SettingRow.CONTACT_US -> parentActivity.openContactMail(R.string.contact) SettingRow.CONTACT_US -> parentActivity.openContactMail(R.string.contact)
SettingRow.BUG_REPORT -> parentActivity.openContactMail(R.string.bug_report_subject) SettingRow.BUG_REPORT -> parentActivity.openContactMail(R.string.bug_report_subject, Realm.getDefaultInstance().path)
SettingRow.CURRENCY -> CurrenciesActivity.newInstanceForResult(this@SettingsFragment, REQUEST_CODE_CURRENCY) SettingRow.CURRENCY -> CurrenciesActivity.newInstanceForResult(this@SettingsFragment, REQUEST_CODE_CURRENCY)
SettingRow.FOLLOW_US -> { SettingRow.FOLLOW_US -> {
when (position) { when (position) {

@ -1,18 +1,11 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="wrap_content" xmlns:tools="http://schemas.android.com/tools"
android:layout_height="wrap_content" android:layout_width="256dp"
android:layout_gravity="center"> android:layout_height="128dp"
android:layout_gravity="center"
<View android:background="@color/colorPrimary">
android:layout_width="128dp"
android:layout_height="128dp"
android:background="@color/colorPrimary"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<androidx.core.widget.ContentLoadingProgressBar <androidx.core.widget.ContentLoadingProgressBar
android:id="@+id/progressBar" android:id="@+id/progressBar"
@ -20,12 +13,30 @@
android:layout_width="32dp" android:layout_width="32dp"
android:layout_height="32dp" android:layout_height="32dp"
android:layout_marginStart="8dp" android:layout_marginStart="8dp"
android:layout_marginTop="8dp" android:layout_marginEnd="8dp"
app:layout_constraintBottom_toTopOf="@+id/loadingMessage"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.5"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_chainStyle="packed" />
<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/loadingMessage"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="8dp"
android:layout_marginTop="16dp"
android:layout_marginEnd="8dp" android:layout_marginEnd="8dp"
android:layout_marginBottom="8dp" android:layout_marginBottom="8dp"
android:fontFamily="@font/roboto"
android:textSize="16sp"
android:text="@string/calculating_please_wait_"
app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.5"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" /> app:layout_constraintTop_toBottomOf="@+id/progressBar"
app:layout_constraintVertical_chainStyle="packed" />
</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<files-path
name="files"
path="." />
</paths>
Loading…
Cancel
Save