diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 90f7c4fd..f304e967 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -64,6 +64,11 @@
android:launchMode="singleTop"
android:screenOrientation="portrait" />
+
+
diff --git a/app/src/main/java/net/pokeranalytics/android/calculus/Calculator.kt b/app/src/main/java/net/pokeranalytics/android/calculus/Calculator.kt
index bb24beb3..03fb0152 100644
--- a/app/src/main/java/net/pokeranalytics/android/calculus/Calculator.kt
+++ b/app/src/main/java/net/pokeranalytics/android/calculus/Calculator.kt
@@ -1,5 +1,8 @@
package net.pokeranalytics.android.calculus
+import android.os.Parcel
+import android.os.Parcelable
+import io.realm.Realm
import net.pokeranalytics.android.calculus.Stat.*
import net.pokeranalytics.android.model.realm.ComputableResult
import net.pokeranalytics.android.model.realm.Filter
@@ -7,6 +10,31 @@ import net.pokeranalytics.android.model.realm.SessionSet
import timber.log.Timber
import java.util.*
+class ParcelableString(var string: String) : Parcelable {
+ constructor(parcel: Parcel) : this(parcel.readString()) {
+ }
+
+ override fun writeToParcel(parcel: Parcel, flags: Int) {
+ parcel.writeString(string)
+ }
+
+ override fun describeContents(): Int {
+ return 0
+ }
+
+ companion object CREATOR : Parcelable.Creator {
+ override fun createFromParcel(parcel: Parcel): ParcelableString {
+ return ParcelableString(parcel)
+ }
+
+ override fun newArray(size: Int): Array {
+ return arrayOfNulls(size)
+ }
+ }
+
+}
+
+
/**
* The class performing stats computation
*/
@@ -59,35 +87,39 @@ class Calculator {
companion object {
- fun computeStatsWithFilters(filters: List, options: Options): List {
+ fun computeStatsWithFilters(realm: Realm, filters: List, options: Options): List {
var computableGroups: MutableList = mutableListOf()
filters.forEach { filter ->
val results = filter.results()
val sets = filter.results()
- val group = ComputableGroup(filter.name, results, sets)
+ val group = ComputableGroup(filter.name, filter.filterConditions.map { it.queryCondition })
computableGroups.add(group)
}
- return Calculator.computeGroups(computableGroups, options)
+ return Calculator.computeGroups(realm, computableGroups, options)
}
/**
* Computes all stats for list of Session sessionGroup
*/
- fun computeGroups(groups: List, options: Options): List {
+ fun computeGroups(realm: Realm, groups: List, options: Options): List {
val computedResults = mutableListOf()
groups.forEach { group ->
val s = Date()
+
+ // Clean existing computables / sessionSets if group is reused
+ group.cleanup()
+
// Computes actual sessionGroup stats
- val results: ComputedResults = Calculator.compute(group, options = options)
+ val results: ComputedResults = Calculator.compute(realm, group, options = options)
// Computes the compared sessionGroup if existing
val comparedGroup = group.comparedComputables
if (comparedGroup != null) {
- val comparedResults = Calculator.compute(comparedGroup, options = options)
+ val comparedResults = Calculator.compute(realm, comparedGroup, options = options)
group.comparedComputedResults = comparedResults
results.computeStatVariations(comparedResults)
}
@@ -107,11 +139,10 @@ class Calculator {
/**
* Computes stats for a SessionSet
*/
- fun compute(computableGroup: ComputableGroup, options: Options): ComputedResults {
-
- Timber.d(">>>> Start computing group ${computableGroup.name}, ${computableGroup.computables.size} computables")
+ fun compute(realm: Realm, computableGroup: ComputableGroup, options: Options): ComputedResults {
- val computables = computableGroup.computables
+ val computables = computableGroup.computables(realm)
+ Timber.d(">>>> Start computing group ${computableGroup.name}, ${computables.size} computables")
val results: ComputedResults = ComputedResults(computableGroup)
@@ -135,30 +166,29 @@ class Calculator {
var tBuyinSum = 0.0
var tHands = 0.0
- computables.forEach { s ->
+ computables.forEach { computable ->
index++
- tSum += s.ratedNet
- tBBSum += s.bbNet
- tBBSessionCount += s.hasBigBlind
- tWinningSessionCount += s.isPositive
- tBuyinSum += s.ratedBuyin
- tHands += s.estimatedHands
-
- results.addEvolutionValue(tSum, NETRESULT, s)
- results.addEvolutionValue(tSum / index, AVERAGE, s)
- results.addEvolutionValue(index.toDouble(), NUMBER_OF_GAMES, s)
- results.addEvolutionValue(tBBSum / tBBSessionCount, AVERAGE_NET_BB, s)
- results.addEvolutionValue((tWinningSessionCount / index).toDouble(), WIN_RATIO, s)
- results.addEvolutionValue(tBuyinSum / index, AVERAGE_BUYIN, s)
-
- val netBB100 = Stat.netBBPer100Hands(tBBSum, tHands)
- if (netBB100 != null) {
- results.addEvolutionValue(netBB100, NET_BB_PER_100_HANDS, s)
+ tSum += computable.ratedNet
+ tBBSum += computable.bbNet
+ tBBSessionCount += computable.hasBigBlind
+ tWinningSessionCount += computable.isPositive
+ tBuyinSum += computable.ratedBuyin
+ tHands += computable.estimatedHands
+
+ val sessionId = ParcelableString(computable.session?.id ?: throw IllegalStateException("Computing lone ComputableResult"))
+ results.addEvolutionValue(tSum, NETRESULT, sessionId)
+ results.addEvolutionValue(tSum / index, AVERAGE, sessionId)
+ results.addEvolutionValue(index.toDouble(), NUMBER_OF_GAMES, sessionId)
+ results.addEvolutionValue(tBBSum / tBBSessionCount, AVERAGE_NET_BB, sessionId)
+ results.addEvolutionValue((tWinningSessionCount / index).toDouble(), WIN_RATIO, sessionId)
+ results.addEvolutionValue(tBuyinSum / index, AVERAGE_BUYIN, sessionId)
+
+ Stat.netBBPer100Hands(tBBSum, tHands)?.let { netBB100 ->
+ results.addEvolutionValue(netBB100, NET_BB_PER_100_HANDS, sessionId)
}
- val roi = Stat.returnOnInvestment(tSum, tBuyinSum)
- if (roi != null) {
- results.addEvolutionValue(roi, ROI, s)
+ Stat.returnOnInvestment(tSum, tBuyinSum)?.let { roi ->
+ results.addEvolutionValue(roi, ROI, sessionId)
}
}
@@ -168,7 +198,7 @@ class Calculator {
}
}
- val sessionSets = computableGroup.sets
+ val sessionSets = computableGroup.sessionSets(realm)
// Compute for each serie
val gHourlyDuration =
@@ -201,20 +231,19 @@ class Calculator {
tHourlyRate = gSum / tHourlyDuration
tHourlyRateBB = gBBSum / tHourlyDuration
- results.addEvolutionValue(tSum, tHourlyDuration, NETRESULT, sessionSet)
- results.addEvolutionValue(tSum / tHourlyDuration, tHourlyDuration, HOURLY_RATE, sessionSet)
- results.addEvolutionValue(tHourlyRate, tHourlyDuration, HOURLY_RATE, sessionSet)
- results.addEvolutionValue(tIndex.toDouble(), tHourlyDuration, NUMBER_OF_SETS, sessionSet)
- results.addEvolutionValue(sessionSet.netDuration.toDouble(), tHourlyDuration, DURATION, sessionSet)
- results.addEvolutionValue(tHourlyDuration / tIndex, tHourlyDuration, AVERAGE_DURATION, sessionSet)
- results.addEvolutionValue(tHourlyRateBB, tHourlyDuration, HOURLY_RATE_BB, sessionSet)
-
- val netBB100 = Stat.netBBPer100Hands(gBBSum, gTotalHands)
- if (netBB100 != null) {
- results.addEvolutionValue(netBB100, tHourlyDuration, NET_BB_PER_100_HANDS, sessionSet)
- } else { //@todo maybe not
- results.addEvolutionValue(0.0, tHourlyDuration, NET_BB_PER_100_HANDS, sessionSet)
+ val id = ParcelableString(sessionSet.id)
+ results.addEvolutionValue(tSum, tHourlyDuration, NETRESULT, id)
+ results.addEvolutionValue(tSum / tHourlyDuration, tHourlyDuration, HOURLY_RATE, id)
+ results.addEvolutionValue(tHourlyRate, tHourlyDuration, HOURLY_RATE, id)
+ results.addEvolutionValue(tIndex.toDouble(), tHourlyDuration, NUMBER_OF_SETS, id)
+ results.addEvolutionValue(sessionSet.netDuration.toDouble(), tHourlyDuration, DURATION, id)
+ results.addEvolutionValue(tHourlyDuration / tIndex, tHourlyDuration, AVERAGE_DURATION, id)
+ results.addEvolutionValue(tHourlyRateBB, tHourlyDuration, HOURLY_RATE_BB, id)
+
+ Stat.netBBPer100Hands(gBBSum, gTotalHands)?.let { netBB100 ->
+ results.addEvolutionValue(netBB100, tHourlyDuration, NET_BB_PER_100_HANDS, id)
}
+
}
}
else -> {
@@ -261,13 +290,10 @@ class Calculator {
)
)
- val roi = Stat.returnOnInvestment(sum, totalBuyin)
- val netBB100 = Stat.netBBPer100Hands(bbSum, totalHands)
-
- if (roi != null) {
+ Stat.returnOnInvestment(sum, totalBuyin)?.let { roi ->
results.addStats(setOf(ComputedStat(ROI, roi)))
}
- if (netBB100 != null) {
+ Stat.netBBPer100Hands(bbSum, totalHands)?.let { netBB100 ->
results.addStats(setOf(ComputedStat(NET_BB_PER_100_HANDS, netBB100)))
}
diff --git a/app/src/main/java/net/pokeranalytics/android/calculus/ComputableGroup.kt b/app/src/main/java/net/pokeranalytics/android/calculus/ComputableGroup.kt
index 6899353c..57b50c37 100644
--- a/app/src/main/java/net/pokeranalytics/android/calculus/ComputableGroup.kt
+++ b/app/src/main/java/net/pokeranalytics/android/calculus/ComputableGroup.kt
@@ -2,161 +2,207 @@ package net.pokeranalytics.android.calculus
import com.github.mikephil.charting.data.BarEntry
import com.github.mikephil.charting.data.Entry
+import io.realm.Realm
import io.realm.RealmResults
+import net.pokeranalytics.android.model.filter.QueryCondition
import net.pokeranalytics.android.model.realm.ComputableResult
+import net.pokeranalytics.android.model.realm.Filter
import net.pokeranalytics.android.model.realm.SessionSet
/**
* A sessionGroup of computable items identified by a name
*/
-class ComputableGroup(name: String, computables: RealmResults, sets: RealmResults, stats: List? = null) {
-
- /**
- * The display name of the group
- */
- var name: String = name
-
- /**
- * The list of endedSessions to compute
- */
- var computables: RealmResults = computables
-
- /**
- * The list of endedSessions to compute
- */
- var sets: RealmResults = sets
-
- /**
- * The list of stats to display
- */
- var stats: List? = stats
-
- /**
- * A subgroup used to compute stat variation
- */
- var comparedComputables: ComputableGroup? = null
-
- /**
- * The computed stats of the comparable sessionGroup
- */
- var comparedComputedResults: ComputedResults? = null
+class ComputableGroup(name: String, conditions: List, stats: List? = null) {
+
+ /**
+ * The display name of the group
+ */
+ var name: String = name
+
+ /**
+ * A list of conditions to get
+ */
+ var conditions: List = conditions
+
+ /**
+ * The list of endedSessions to compute
+ */
+ private var _computables: RealmResults? = null
+
+ /**
+ * Retrieves the computables on the relative [realm] filtered with the provided [conditions]
+ */
+ fun computables(realm: Realm): RealmResults {
+
+ // if computables exists and is valid (previous realm not closed)
+ this._computables?.let {
+ if (it.isValid) {
+ return it
+ }
+ }
+
+ val computables: RealmResults = Filter.queryOn(realm, this.conditions)
+ this._computables = computables
+ return computables
+ }
+
+ /**
+ * The list of sets to compute
+ */
+ private var _sessionSets: RealmResults? = null
+
+ /**
+ * Retrieves the session sets on the relative [realm] filtered with the provided [conditions]
+ */
+ fun sessionSets(realm: Realm): RealmResults {
+ // if computables exists and is valid (previous realm not closed)
+ this._sessionSets?.let {
+ if (it.isValid) {
+ return it
+ }
+ }
+
+ val sets: RealmResults = Filter.queryOn(realm, this.conditions)
+ this._sessionSets = sets
+ return sets
+ }
+
+ /**
+ * The list of stats to display
+ */
+ var stats: List? = stats
+
+ /**
+ * A subgroup used to compute stat variation
+ */
+ var comparedComputables: ComputableGroup? = null
+
+ /**
+ * The computed stats of the comparable sessionGroup
+ */
+ var comparedComputedResults: ComputedResults? = null
+
+ fun cleanup() {
+ this._computables = null
+ this._sessionSets = null
+ }
}
class ComputedResults(group: ComputableGroup) {
- /**
- * The session group used to computed the stats
- */
- var group: ComputableGroup = group
-
- // The computed stats of the sessionGroup
- private var _computedStats: MutableMap = mutableMapOf()
-
- // The map containing all evolution numericValues for all stats
- private var _evolutionValues: MutableMap> = mutableMapOf()
-
- fun allStats() : Collection {
- return this._computedStats.values
- }
-
- /**
- * Adds a value to the evolution values
- */
- fun addEvolutionValue(value: Double, stat: Stat, data: Any) {
- this._addEvolutionValue(Point(value, data), stat = stat)
- }
-
- fun addEvolutionValue(value: Double, duration: Double, stat: Stat, data: Any) {
- this._addEvolutionValue(Point(value, y = duration, data = data), stat = stat)
- }
-
- private fun _addEvolutionValue(point: Point, stat: Stat) {
- val evolutionValues = this._evolutionValues[stat]
- if (evolutionValues != null) {
- evolutionValues.add(point)
- } else {
- val values: MutableList = mutableListOf(point)
- this._evolutionValues[stat] = values
- }
- }
-
- fun addStats(computedStats: Set) {
- computedStats.forEach {
- this._computedStats[it.stat] = it
- }
- }
-
- fun computedStat(stat: Stat) : ComputedStat? {
- return this._computedStats[stat]
- }
-
- fun computeStatVariations(resultsToCompare: ComputedResults) {
- this._computedStats.keys.forEach { stat ->
- val computedStat = this.computedStat(stat)
- val comparedStat = resultsToCompare.computedStat(stat)
- if (computedStat != null && comparedStat != null) {
- computedStat.variation = (computedStat.value - comparedStat.value) / comparedStat.value
- }
- }
- }
-
- fun finalize(options: Calculator.Options) {
- if (options.evolutionValues != Calculator.Options.EvolutionValues.NONE) {
-
- // Sort points as a distribution
- this._computedStats.keys.filter { it.hasDistributionSorting() }.forEach { _ ->
- // @todo sort
+ /**
+ * The session group used to computed the stats
+ */
+ var group: ComputableGroup = group
+
+ // The computed stats of the sessionGroup
+ private var _computedStats: MutableMap = mutableMapOf()
+
+ // The map containing all evolution numericValues for all stats
+ private var _evolutionValues: MutableMap> = mutableMapOf()
+
+ fun allStats(): Collection {
+ return this._computedStats.values
+ }
+
+ /**
+ * Adds a value to the evolution values
+ */
+ fun addEvolutionValue(value: Double, stat: Stat, data: Any) {
+ this._addEvolutionValue(Point(value, data), stat = stat)
+ }
+
+ fun addEvolutionValue(value: Double, duration: Double, stat: Stat, data: Any) {
+ this._addEvolutionValue(Point(value, y = duration, data = data), stat = stat)
+ }
+
+ private fun _addEvolutionValue(point: Point, stat: Stat) {
+ val evolutionValues = this._evolutionValues[stat]
+ if (evolutionValues != null) {
+ evolutionValues.add(point)
+ } else {
+ val values: MutableList = mutableListOf(point)
+ this._evolutionValues[stat] = values
+ }
+ }
+
+ fun addStats(computedStats: Set) {
+ computedStats.forEach {
+ this._computedStats[it.stat] = it
+ }
+ }
+
+ fun computedStat(stat: Stat): ComputedStat? {
+ return this._computedStats[stat]
+ }
+
+ fun computeStatVariations(resultsToCompare: ComputedResults) {
+ this._computedStats.keys.forEach { stat ->
+ val computedStat = this.computedStat(stat)
+ val comparedStat = resultsToCompare.computedStat(stat)
+ if (computedStat != null && comparedStat != null) {
+ computedStat.variation = (computedStat.value - comparedStat.value) / comparedStat.value
+ }
+ }
+ }
+
+ fun finalize(options: Calculator.Options) {
+ if (options.evolutionValues != Calculator.Options.EvolutionValues.NONE) {
+
+ // Sort points as a distribution
+ this._computedStats.keys.filter { it.hasDistributionSorting() }.forEach { _ ->
+ // @todo sort
// var evolutionValues = this._evolutionValues[stat]
// evolutionValues.so
- }
+ }
- }
- }
+ }
+ }
- /**
- * Returns the number of computed stats
- */
- fun numberOfStats() : Int {
- return this._computedStats.size
- }
+ /**
+ * Returns the number of computed stats
+ */
+ fun numberOfStats(): Int {
+ return this._computedStats.size
+ }
// MPAndroidChart
- fun defaultStatEntries(stat: Stat) : Array {
+ fun defaultStatEntries(stat: Stat): List {
return when (stat) {
Stat.NUMBER_OF_SETS, Stat.NUMBER_OF_GAMES -> this.barEntries(stat)
else -> this.singleLineEntries(stat)
}
}
- fun singleLineEntries(stat: Stat) : Array {
+ fun singleLineEntries(stat: Stat): List {
var entries = mutableListOf()
this._evolutionValues[stat]?.let { points ->
points.forEachIndexed { index, p ->
entries.add(Entry(index.toFloat(), p.y.toFloat(), p.data))
}
}
- return entries.toTypedArray()
+ return entries
}
- fun durationEntries(stat: Stat) : Array {
+ fun durationEntries(stat: Stat): List {
var entries = mutableListOf()
this._evolutionValues[stat]?.let { points ->
points.forEach { p ->
entries.add(Entry(p.x.toFloat(), p.y.toFloat(), p.data))
}
}
- return entries.toTypedArray()
+ return entries
}
- fun barEntries(stat: Stat) : Array {
+ fun barEntries(stat: Stat): List {
- var entries = arrayOf()
+ var entries = mutableListOf()
this._evolutionValues[stat]?.let { points ->
points.forEach { p ->
- entries[0] = BarEntry(p.x.toFloat(), p.y.toFloat(), p.data)
+ entries.add(BarEntry(p.x.toFloat(), p.y.toFloat(), p.data))
}
}
return entries
diff --git a/app/src/main/java/net/pokeranalytics/android/model/migrations/PokerAnalyticsMigration.kt b/app/src/main/java/net/pokeranalytics/android/model/migrations/PokerAnalyticsMigration.kt
index 77d26c60..d27daf72 100644
--- a/app/src/main/java/net/pokeranalytics/android/model/migrations/PokerAnalyticsMigration.kt
+++ b/app/src/main/java/net/pokeranalytics/android/model/migrations/PokerAnalyticsMigration.kt
@@ -40,6 +40,10 @@ class PokerAnalyticsMigration : RealmMigration {
schema.get("Filter")?.let {
it.renameField("filterElements", "filterConditions")
}
+ schema.get("SessionSet")?.let {
+ it.addPrimaryKey("id")
+ }
+
currentVersion++
}
diff --git a/app/src/main/java/net/pokeranalytics/android/model/realm/ComputableResult.kt b/app/src/main/java/net/pokeranalytics/android/model/realm/ComputableResult.kt
index 427621d8..e0786847 100644
--- a/app/src/main/java/net/pokeranalytics/android/model/realm/ComputableResult.kt
+++ b/app/src/main/java/net/pokeranalytics/android/model/realm/ComputableResult.kt
@@ -1,13 +1,11 @@
package net.pokeranalytics.android.model.realm
-import android.os.Parcel
-import android.os.Parcelable
import io.realm.RealmObject
import net.pokeranalytics.android.calculus.interfaces.Computable
import net.pokeranalytics.android.model.filter.Filterable
import net.pokeranalytics.android.model.filter.QueryCondition
-open class ComputableResult() : RealmObject(), Computable, Filterable, Parcelable {
+open class ComputableResult() : RealmObject(), Computable, Filterable {
override var ratedNet: Double = 0.0
@@ -27,16 +25,6 @@ open class ComputableResult() : RealmObject(), Computable, Filterable, Parcelabl
var session: Session? = null
- constructor(parcel: Parcel) : this() {
- ratedNet = parcel.readDouble()
- bbNet = parcel.readDouble()
- hasBigBlind = parcel.readInt()
- isPositive = parcel.readInt()
- ratedBuyin = parcel.readDouble()
- estimatedHands = parcel.readDouble()
- bbPer100Hands = parcel.readDouble()
- }
-
fun updateWith(session: Session) {
this.sessionSet = session.sessionSet
@@ -66,28 +54,7 @@ open class ComputableResult() : RealmObject(), Computable, Filterable, Parcelabl
BB_PER100HANDS("bbPer100Hands")
}
- override fun writeToParcel(parcel: Parcel, flags: Int) {
- parcel.writeDouble(ratedNet)
- parcel.writeDouble(bbNet)
- parcel.writeInt(hasBigBlind)
- parcel.writeInt(isPositive)
- parcel.writeDouble(ratedBuyin)
- parcel.writeDouble(estimatedHands)
- parcel.writeDouble(bbPer100Hands)
- }
-
- override fun describeContents(): Int {
- return 0
- }
-
- companion object CREATOR : Parcelable.Creator, Filterable {
- override fun createFromParcel(parcel: Parcel): ComputableResult {
- return ComputableResult(parcel)
- }
-
- override fun newArray(size: Int): Array {
- return arrayOfNulls(size)
- }
+ companion object : Filterable {
fun fieldNameForQueryType(queryCondition: QueryCondition): String? {
return "session." + Session.fieldNameForQueryType(queryCondition)
diff --git a/app/src/main/java/net/pokeranalytics/android/model/realm/Filter.kt b/app/src/main/java/net/pokeranalytics/android/model/realm/Filter.kt
index 9ccaa0a0..c962b609 100644
--- a/app/src/main/java/net/pokeranalytics/android/model/realm/Filter.kt
+++ b/app/src/main/java/net/pokeranalytics/android/model/realm/Filter.kt
@@ -10,6 +10,7 @@ import net.pokeranalytics.android.ui.view.rowrepresentable.FilterCategoryRow
import net.pokeranalytics.android.ui.view.rowrepresentable.FilterElementRow
import net.pokeranalytics.android.ui.view.rowrepresentable.FilterSectionRow
import org.jetbrains.annotations.TestOnly
+import timber.log.Timber
import java.util.*
/**
@@ -43,8 +44,9 @@ open class Filter : RealmObject() {
inline fun queryOn(realm: Realm, queries: List): RealmResults {
var realmQuery = realm.where()
queries.forEach {
- realmQuery = it.filter(realmQuery)
+ realmQuery = it.filter(realmQuery)
}
+ Timber.d(">>> Filter query: ${realmQuery.description}")
return realmQuery.findAll()
}
}
diff --git a/app/src/main/java/net/pokeranalytics/android/model/realm/SessionSet.kt b/app/src/main/java/net/pokeranalytics/android/model/realm/SessionSet.kt
index eee014a1..6a3ae55d 100644
--- a/app/src/main/java/net/pokeranalytics/android/model/realm/SessionSet.kt
+++ b/app/src/main/java/net/pokeranalytics/android/model/realm/SessionSet.kt
@@ -1,19 +1,21 @@
package net.pokeranalytics.android.model.realm
-import android.os.Parcel
-import android.os.Parcelable
import io.realm.Realm
import io.realm.RealmObject
import io.realm.RealmResults
import io.realm.annotations.Ignore
import io.realm.annotations.LinkingObjects
+import io.realm.annotations.PrimaryKey
import net.pokeranalytics.android.model.filter.Filterable
import net.pokeranalytics.android.model.filter.QueryCondition
import net.pokeranalytics.android.model.interfaces.Timed
import java.util.*
-open class SessionSet() : RealmObject(), Timed, Filterable, Parcelable {
+open class SessionSet() : RealmObject(), Timed, Filterable {
+
+ @PrimaryKey
+ var id = UUID.randomUUID().toString()
var startDate: Date = Date()
set(value) {
@@ -72,13 +74,6 @@ open class SessionSet() : RealmObject(), Timed, Filterable, Parcelable {
var bbNet: Double = 0.0
- constructor(parcel: Parcel) : this() {
- netDuration = parcel.readLong()
- ratedNet = parcel.readDouble()
- estimatedHands = parcel.readDouble()
- bbNet = parcel.readDouble()
- }
-
enum class Field(val identifier: String) {
RATED_NET("ratedNet"),
HOURLY_RATE("hourlyRate"),
@@ -87,31 +82,10 @@ open class SessionSet() : RealmObject(), Timed, Filterable, Parcelable {
NET_DURATION("netDuration")
}
- override fun writeToParcel(parcel: Parcel, flags: Int) {
- parcel.writeLong(netDuration)
- parcel.writeDouble(ratedNet)
- parcel.writeDouble(estimatedHands)
- parcel.writeDouble(bbNet)
- }
-
- override fun describeContents(): Int {
- return 0
- }
-
- companion object CREATOR : Parcelable.Creator, Filterable {
-
- override fun createFromParcel(parcel: Parcel): SessionSet {
- return SessionSet(parcel)
- }
-
- override fun newArray(size: Int): Array {
- return arrayOfNulls(size)
- }
-
- // Filterable
+ companion object : Filterable {
fun newInstance(realm: Realm) : SessionSet {
- val sessionSet: SessionSet = realm.createObject(SessionSet::class.java)
+ val sessionSet = SessionSet()
return realm.copyToRealm(sessionSet)
}
diff --git a/app/src/main/java/net/pokeranalytics/android/ui/activity/GraphActivity.kt b/app/src/main/java/net/pokeranalytics/android/ui/activity/GraphActivity.kt
index 4de9e896..4140b81a 100644
--- a/app/src/main/java/net/pokeranalytics/android/ui/activity/GraphActivity.kt
+++ b/app/src/main/java/net/pokeranalytics/android/ui/activity/GraphActivity.kt
@@ -9,6 +9,11 @@ import net.pokeranalytics.android.calculus.Stat
import net.pokeranalytics.android.ui.activity.components.PokerAnalyticsActivity
import net.pokeranalytics.android.ui.fragment.GraphFragment
+class GraphParameters(stat: Stat, entries: List) {
+ var stat: Stat = stat
+ var entries: List = entries
+}
+
class GraphActivity : PokerAnalyticsActivity() {
private enum class IntentKey(val keyName: String) {
@@ -18,13 +23,17 @@ class GraphActivity : PokerAnalyticsActivity() {
companion object {
+ // Unparcel fails when setting a custom Parcelable object on Entry so we use a static reference to passe objects
+ var parameters: GraphParameters? = null
+
/**
* Default constructor
*/
- fun newInstance(context: Context, stat: Stat, entries: Array) {
+ fun newInstance(context: Context, stat: Stat, entries: List) {
+
+ GraphActivity.parameters = GraphParameters(stat, entries)
+
val intent = Intent(context, GraphActivity::class.java)
- intent.putExtra(IntentKey.STAT.keyName, stat.name)
- intent.putExtra(IntentKey.ENTRIES.keyName, entries)
context.startActivity(intent)
}
@@ -41,16 +50,19 @@ class GraphActivity : PokerAnalyticsActivity() {
*/
private fun initUI() {
- val stat = Stat.valueOf(intent.getStringExtra(IntentKey.STAT.keyName))
- val entries = intent.getParcelableArrayExtra(IntentKey.ENTRIES.keyName)
-
val fragmentManager = supportFragmentManager
val fragmentTransaction = fragmentManager.beginTransaction()
val fragment = GraphFragment()
fragmentTransaction.add(R.id.container, fragment)
fragmentTransaction.commit()
- fragment.setData(stat, entries)
+
+ GraphActivity.parameters?.let {
+ fragment.setData(it.stat, it.entries)
+ GraphActivity.parameters = null
+ } ?: run {
+ throw Exception("Missing graph parameters")
+ }
}
diff --git a/app/src/main/java/net/pokeranalytics/android/ui/fragment/GraphFragment.kt b/app/src/main/java/net/pokeranalytics/android/ui/fragment/GraphFragment.kt
index fc2bd3c8..4f713c6e 100644
--- a/app/src/main/java/net/pokeranalytics/android/ui/fragment/GraphFragment.kt
+++ b/app/src/main/java/net/pokeranalytics/android/ui/fragment/GraphFragment.kt
@@ -1,7 +1,6 @@
package net.pokeranalytics.android.ui.fragment
import android.os.Bundle
-import android.os.Parcelable
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
@@ -21,16 +20,16 @@ interface GraphDataSource {
class GraphFragment : PokerAnalyticsFragment() {
lateinit var dataSource: GraphDataSource
- lateinit var entries: Array
+
lateinit var stat: Stat
+ lateinit var entries: List
companion object {
-
}
- fun setData(stat: Stat, entries: Array) {
+ fun setData(stat: Stat, entries: List) {
this.stat = stat
this.entries = entries
}
@@ -46,13 +45,9 @@ class GraphFragment : PokerAnalyticsFragment() {
private fun initUI() {
- (this.entries.toList() as MutableList).let { entries ->
-
- val dataSet = LineDataSet(entries, stat.name)
- val lineData = LineData(listOf(dataSet))
- this.chart.data = lineData
-
- }
+ val dataSet = LineDataSet(this.entries, this.stat.name)
+ val lineData = LineData(listOf(dataSet))
+ this.chart.data = lineData
}
diff --git a/app/src/main/java/net/pokeranalytics/android/ui/fragment/StatsFragment.kt b/app/src/main/java/net/pokeranalytics/android/ui/fragment/StatsFragment.kt
index afb7845e..000e43de 100644
--- a/app/src/main/java/net/pokeranalytics/android/ui/fragment/StatsFragment.kt
+++ b/app/src/main/java/net/pokeranalytics/android/ui/fragment/StatsFragment.kt
@@ -11,9 +11,7 @@ import kotlinx.coroutines.*
import net.pokeranalytics.android.R
import net.pokeranalytics.android.calculus.*
import net.pokeranalytics.android.model.StatRepresentable
-import net.pokeranalytics.android.model.realm.ComputableResult
-import net.pokeranalytics.android.model.realm.Session
-import net.pokeranalytics.android.model.realm.SessionSet
+import net.pokeranalytics.android.model.filter.QueryCondition
import net.pokeranalytics.android.ui.activity.GraphActivity
import net.pokeranalytics.android.ui.adapter.DisplayDescriptor
import net.pokeranalytics.android.ui.adapter.RowRepresentableAdapter
@@ -165,32 +163,16 @@ class StatsFragment : SessionObserverFragment(), StaticRowRepresentableDataSourc
private fun createSessionGroupsAndStartCompute(realm: Realm) : List {
- val s = Date()
-
- val allSessions = realm.where(ComputableResult::class.java).findAll()
- val allSessionSets = realm.where(SessionSet::class.java).findAll()
- Timber.d(">>>>> number of computables to compute = ${allSessions.size}")
-
- val cgSessions = allSessions.where().equalTo("session.type", Session.Type.CASH_GAME.ordinal).findAll()
- val cgSessionSets = realm.where(SessionSet::class.java).equalTo("sessions.type", Session.Type.CASH_GAME.ordinal).findAll()
-
- val tSessions = allSessions.where().equalTo("session.type", Session.Type.TOURNAMENT.ordinal).findAll()
- val tSessionSets = realm.where(SessionSet::class.java).equalTo("sessions.type", Session.Type.TOURNAMENT.ordinal).findAll()
-
- val e = Date()
- val duration = (e.time - s.time) / 1000.0
- Timber.d(">>> filtering in ${duration} seconds")
-
val allStats: List = listOf(Stat.NETRESULT, Stat.HOURLY_RATE, Stat.AVERAGE, Stat.NUMBER_OF_SETS, Stat.AVERAGE_DURATION, Stat.DURATION)
- val allSessionGroup = ComputableGroup(stringAll, allSessions, allSessionSets, allStats)
+ val allSessionGroup = ComputableGroup(stringAll, listOf(), allStats)
val cgStats: List = listOf(Stat.NETRESULT, Stat.HOURLY_RATE, Stat.NET_BB_PER_100_HANDS, Stat.HOURLY_RATE_BB, Stat.AVERAGE, Stat.STANDARD_DEVIATION_HOURLY, Stat.WIN_RATIO, Stat.NUMBER_OF_GAMES, Stat.AVERAGE_BUYIN)
- val cgSessionGroup = ComputableGroup(stringCashGame, cgSessions, cgSessionSets, cgStats)
+ val cgSessionGroup = ComputableGroup(stringCashGame, listOf(QueryCondition.CASH), cgStats)
val tStats: List = listOf(Stat.NETRESULT, Stat.HOURLY_RATE, Stat.ROI, Stat.WIN_RATIO, Stat.NUMBER_OF_GAMES, Stat.AVERAGE_BUYIN)
- val tSessionGroup = ComputableGroup(stringTournament, tSessions, tSessionSets, tStats)
+ val tSessionGroup = ComputableGroup(stringTournament, listOf(QueryCondition.TOURNAMENT), tStats)
Timber.d(">>>>> Start computations...")
- return Calculator.computeGroups(listOf(allSessionGroup, cgSessionGroup, tSessionGroup), Calculator.Options())
+ return Calculator.computeGroups(realm, listOf(allSessionGroup, cgSessionGroup, tSessionGroup), Calculator.Options())
}
@@ -217,8 +199,6 @@ class StatsFragment : SessionObserverFragment(), StaticRowRepresentableDataSourc
override fun onRowSelected(position: Int, row: RowRepresentable, fromAction: Boolean) {
- return
-
if (row is StatRepresentable) {
// filter groups
@@ -245,7 +225,7 @@ class StatsFragment : SessionObserverFragment(), StaticRowRepresentableDataSourc
val realm = Realm.getDefaultInstance()
val options = Calculator.Options()
options.evolutionValues = Calculator.Options.EvolutionValues.STANDARD
- results = Calculator.computeGroups(listOf(computableGroup), options)
+ results = Calculator.computeGroups(realm, listOf(computableGroup), options)
realm.close()
val e = Date()