diff --git a/.idea/deploymentTargetDropDown.xml b/.idea/deploymentTargetDropDown.xml index 8fe6b1f8cbd1c0e3ed3657a079a63b702130ea7e..279d637d306ec5a712dc1926ce90ef108089289c 100644 --- a/.idea/deploymentTargetDropDown.xml +++ b/.idea/deploymentTargetDropDown.xml @@ -1,17 +1,17 @@ <?xml version="1.0" encoding="UTF-8"?> <project version="4"> <component name="deploymentTargetDropDown"> - <runningDeviceTargetSelectedWithDropDown> + <targetSelectedWithDropDown> <Target> - <type value="RUNNING_DEVICE_TARGET" /> + <type value="QUICK_BOOT_TARGET" /> <deviceKey> <Key> - <type value="SERIAL_NUMBER" /> - <value value="BH901SF58Z" /> + <type value="VIRTUAL_DEVICE_PATH" /> + <value value="$USER_HOME$/.android/avd/Pixel_4_API_30.avd" /> </Key> </deviceKey> </Target> - </runningDeviceTargetSelectedWithDropDown> - <timeTargetWasSelectedWithDropDown value="2021-12-14T14:31:07.475808Z" /> + </targetSelectedWithDropDown> + <timeTargetWasSelectedWithDropDown value="2021-12-19T13:56:45.956907Z" /> </component> </project> \ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml index 974d01916b38447562616854a09e5863c8bd6f05..8de1e05005ee4b57ed32e8fe3389ca81be8ba418 100644 --- a/.idea/misc.xml +++ b/.idea/misc.xml @@ -26,8 +26,23 @@ <entry key="../../../../layout/compose-model-1638879424123.xml" value="0.15625" /> <entry key="../../../../layout/compose-model-1638892987664.xml" value="0.1570945945945946" /> <entry key="../../../../layout/compose-model-1638894001064.xml" value="0.165" /> - <entry key="../../../../layout/compose-model-1639493007794.xml" value="0.45692567567567566" /> - <entry key="../../../../layout/compose-model-1639493742130.xml" value="0.22596153846153846" /> + <entry key="../../../../layout/compose-model-1639090066256.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1639500336802.xml" value="0.1570945945945946" /> + <entry key="../../../../layout/compose-model-1639508366252.xml" value="0.25" /> + <entry key="../../../../layout/compose-model-1639671880070.xml" value="0.1492776886035313" /> + <entry key="../../../../layout/compose-model-1639732824378.xml" value="0.1570945945945946" /> + <entry key="../../../../layout/compose-model-1639733405340.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1639735315421.xml" value="0.15625" /> + <entry key="../../../../layout/compose-model-1639735659789.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1639736217744.xml" value="0.165" /> + <entry key="../../../../layout/compose-model-1639736217747.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1639758756856.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1639950739064.xml" value="0.165" /> + <entry key="../../../../layout/compose-model-1639950739400.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1640168674266.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1640171994534.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1640172762520.xml" value="0.1" /> + <entry key="../../../../layout/compose-model-1640173242456.xml" value="0.1" /> <entry key="app/src/main/res/layout/activity_create_character.xml" value="0.16510416666666666" /> <entry key="app/src/main/res/layout/activity_main.xml" value="0.16510416666666666" /> <entry key="app/src/main/res/layout/activity_profile.xml" value="0.165" /> diff --git a/app/build.gradle b/app/build.gradle index c1f2f0b725892d15df2b34a1e86741dba0809ad0..e47c944b16c64702095fc1f4e36ad00b4ceffee5 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -3,6 +3,7 @@ plugins { id 'kotlin-android' id 'kotlin-kapt' id "kotlinx-serialization" + id 'com.google.gms.google-services' } android { @@ -62,12 +63,13 @@ dependencies { implementation 'com.google.android.material:material:1.4.0' implementation 'androidx.constraintlayout:constraintlayout:2.1.2' implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.4.0' - implementation "org.jetbrains.kotlinx:kotlinx-serialization-json:1.2.2" + implementation 'org.jetbrains.kotlinx:kotlinx-serialization-json:1.3.1' implementation 'androidx.activity:activity-compose:1.4.0' implementation "androidx.compose.ui:ui:$compose_version" implementation "androidx.compose.material:material:$compose_version" implementation "androidx.compose.material3:material3:1.0.0-alpha02" implementation "androidx.compose.ui:ui-tooling-preview:$compose_version" + implementation 'com.google.firebase:firebase-analytics:17.2.2' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' @@ -75,7 +77,7 @@ dependencies { androidTestImplementation "androidx.compose.ui:ui-test-junit4:$compose_version" debugImplementation "androidx.compose.ui:ui-tooling:$compose_version" - def room_version = '2.3.0' + def room_version = '2.4.0' implementation "androidx.room:room-runtime:$room_version" kapt "androidx.room:room-compiler:$room_version" @@ -86,4 +88,8 @@ dependencies { implementation "androidx.compose.runtime:runtime-livedata:$compose_version" // Coroutine implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-core:1.5.2' + + // Firebase + implementation platform('com.google.firebase:firebase-bom:29.0.3') + implementation 'com.google.firebase:firebase-analytics-ktx' } \ No newline at end of file diff --git a/app/google-services.json b/app/google-services.json new file mode 100644 index 0000000000000000000000000000000000000000..ce3e93a12325bc7726c7dd6ca2fa9c52d5b4f300 --- /dev/null +++ b/app/google-services.json @@ -0,0 +1,39 @@ +{ + "project_info": { + "project_number": "853904020533", + "project_id": "dnd-spell-book-df615", + "storage_bucket": "dnd-spell-book-df615.appspot.com" + }, + "client": [ + { + "client_info": { + "mobilesdk_app_id": "1:853904020533:android:d64c8a502392471e8dcd7c", + "android_client_info": { + "package_name": "com.flyinpancake.dndspells" + } + }, + "oauth_client": [ + { + "client_id": "853904020533-cf632uohsm9ui5doluo72m1umu3j6ion.apps.googleusercontent.com", + "client_type": 3 + } + ], + "api_key": [ + { + "current_key": "AIzaSyARZa97pugpKQF6S6wC8Umwbn1vu8Mti0M" + } + ], + "services": { + "appinvite_service": { + "other_platform_oauth_client": [ + { + "client_id": "853904020533-cf632uohsm9ui5doluo72m1umu3j6ion.apps.googleusercontent.com", + "client_type": 3 + } + ] + } + } + } + ], + "configuration_version": "1" +} \ No newline at end of file diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 70a3f85114735e9b35eccc132ab16665de304e6f..2ca54a6b0b059744ece2e94f56730e8d00040c39 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -13,11 +13,6 @@ android:roundIcon="@mipmap/ic_launcher_round" android:supportsRtl="true" android:theme="@style/Theme.DndSpells"> - <activity - android:name=".RuinableActivity" - android:exported="false" - android:label="@string/title_activity_ruinable" - android:theme="@style/Theme.DndSpells.NoActionBar" /> <activity android:name=".SelectSpellsActivity" android:exported="false" @@ -38,9 +33,6 @@ android:exported="false" android:label="@string/title_activity_create_character" android:theme="@style/Theme.DndSpells.NoActionBar" /> - <activity - android:name=".ProfileActivity" - android:exported="false" /> <activity android:name=".MainActivity" android:exported="true"> diff --git a/app/src/main/java/com/flyinpancake/dndspells/CharacterDetailsActivity.kt b/app/src/main/java/com/flyinpancake/dndspells/CharacterDetailsActivity.kt index f56cfff858aba2555e63ccc633542926134fa9db..eb0970cb8da50d7073f95990ddaa7967b54cb341 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/CharacterDetailsActivity.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/CharacterDetailsActivity.kt @@ -5,10 +5,7 @@ import android.content.Intent import android.os.Bundle import androidx.activity.ComponentActivity import androidx.activity.compose.setContent -import androidx.compose.foundation.layout.Row -import androidx.compose.foundation.layout.fillMaxSize -import androidx.compose.foundation.layout.fillMaxWidth -import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.* import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.foundation.lazy.items import androidx.compose.material.* @@ -16,23 +13,38 @@ import androidx.compose.material.icons.Icons import androidx.compose.material.icons.outlined.Add import androidx.compose.runtime.Composable import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.runtime.rememberCoroutineScope import androidx.compose.ui.Modifier import androidx.compose.ui.platform.LocalContext +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.res.stringResource import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp import androidx.lifecycle.ViewModelProvider import com.flyinpancake.dndspells.CharacterDetailsActivity.Companion.KEY_NAME import com.flyinpancake.dndspells.model.DndCharacter import com.flyinpancake.dndspells.model.Spell +import com.flyinpancake.dndspells.ui.components.DndTopBar +import com.flyinpancake.dndspells.ui.components.SpellContent import com.flyinpancake.dndspells.ui.theme.DndSpellsTheme import com.flyinpancake.dndspells.viewmodel.CharacterViewModel import com.flyinpancake.dndspells.viewmodel.SpellViewModel +import kotlinx.coroutines.launch import kotlinx.serialization.ExperimentalSerializationApi -import kotlinx.serialization.encodeToString -import kotlinx.serialization.json.Json -import java.util.* +import kotlin.random.Random +fun roll(rollText: String): String { + var sum = 0 + val diceCount = rollText.split("d")[0].toInt() + val diceSides = rollText.split("d")[1].toInt() + + for (ii in 1..diceCount) + sum += Random.nextInt(from = 1, until = diceSides+1 ) + + return sum.toString() +} + class CharacterDetailsActivity : ComponentActivity() { companion object { const val KEY_NAME = "KEY_NAME" @@ -62,6 +74,9 @@ class CharacterDetailsActivity : ComponentActivity() { fun CharacterDetailContent(character: DndCharacter = DndCharacter(), spells: List<Spell> = listOf()) { val activity = (LocalContext.current as? Activity) + val scaffoldState = rememberScaffoldState() + val coroutineScope = rememberCoroutineScope() + Scaffold( topBar = { DndTopBar(character.name) }, floatingActionButton = { @@ -77,18 +92,33 @@ fun CharacterDetailContent(character: DndCharacter = DndCharacter(), spells: Lis } ) }, + scaffoldState = scaffoldState, ) { - CharacterSpellList(spells = spells, character = character, onItemClick = { spell -> - val intent = Intent(activity, SpellDetailsActivity::class.java) - intent.putExtra(SpellDetailsActivity.KEY_SPELLNAME, Json.encodeToString(spell)) - activity?.startActivity(intent) - }) + val youRolled = stringResource(R.string.you_rolled) + CharacterSpellList( + spells = spells, + character = character, + onItemClick = { spell -> + val intent = Intent(activity, SpellDetailsActivity::class.java) + intent.putExtra(SpellDetailsActivity.KEY_SPELL_NAME, spell.name) + activity?.startActivity(intent) + }, + onRoll = { spell -> + coroutineScope.launch { + scaffoldState.snackbarHostState.showSnackbar(youRolled + roll(spell.roll!!.trim())) + } + } + ) } } @OptIn(ExperimentalMaterialApi::class) @Composable -fun SpellListItem(spell: Spell, onItemClick: (Spell) -> Unit = {}) { +fun SpellListItem( + spell: Spell, + onItemClick: (Spell) -> Unit = {}, + onRoll: (Spell) -> Unit = {}, +){ Card( modifier = Modifier .fillMaxWidth() @@ -99,17 +129,34 @@ fun SpellListItem(spell: Spell, onItemClick: (Spell) -> Unit = {}) { Modifier .fillMaxSize() .padding(10.dp), + horizontalArrangement = Arrangement.SpaceBetween ) { + spell.roll?.let { + IconButton( + onClick = { onRoll(spell) }, + Modifier.padding(end = 2.dp) + ) { + Icon( + painter = painterResource(id = R.drawable.dice_5_outline), + contentDescription = "Roll", + ) + } + } SpellContent(spell = spell) } } } @Composable -fun CharacterSpellList(character: DndCharacter, spells: List<Spell>, onItemClick: (Spell) -> Unit = {} ) { - LazyColumn() { +fun CharacterSpellList( + character: DndCharacter, + spells: List<Spell>, + onItemClick: (Spell) -> Unit = {}, + onRoll: (Spell) -> Unit = {}, +) { + LazyColumn { items(spells.filter { character.spellList.contains(it.name) }) { - SpellListItem(it, onItemClick) + SpellListItem(it, onItemClick, onRoll) } } } @@ -118,6 +165,6 @@ fun CharacterSpellList(character: DndCharacter, spells: List<Spell>, onItemClick @Composable fun CharacterDetailPreview() { DndSpellsTheme { - CharacterDetailContent(sampleCharacter, samplespells) + CharacterDetailContent(sampleCharacter, sampleSpells) } } \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/CreateCharacterActivity.kt b/app/src/main/java/com/flyinpancake/dndspells/CreateCharacterActivity.kt index 69f9456ee18f16f4f468a55b0f4ba6fdf75186a5..74f825d73ae3bc8f3cbbc7158f3c49a3581b59bc 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/CreateCharacterActivity.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/CreateCharacterActivity.kt @@ -8,19 +8,23 @@ import androidx.compose.foundation.layout.* import androidx.compose.material.* import androidx.compose.material.icons.Icons import androidx.compose.material.icons.outlined.Add -import androidx.compose.material.icons.outlined.ArrowBack +import androidx.compose.material.icons.outlined.Delete import androidx.compose.material.icons.outlined.Edit import androidx.compose.runtime.* import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.res.stringResource -import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp +import androidx.lifecycle.LiveData import androidx.lifecycle.ViewModelProvider -import androidx.navigation.findNavController import com.flyinpancake.dndspells.model.DndCharacter +import com.flyinpancake.dndspells.model.DndClass +import com.flyinpancake.dndspells.ui.components.ClassSelector +import com.flyinpancake.dndspells.ui.components.DndTopBar +import com.flyinpancake.dndspells.ui.components.LevelSelector import com.flyinpancake.dndspells.ui.theme.DndSpellsTheme import com.flyinpancake.dndspells.viewmodel.CharacterViewModel import kotlinx.coroutines.CoroutineScope @@ -32,37 +36,62 @@ fun addNewCharacter(character: DndCharacter) { characterViewModel.insert(character) } -fun updateCharacter(character: DndCharacter) { - characterViewModel.update(character) -} - -@ExperimentalMaterialApi class CreateCharacterActivity : ComponentActivity() { companion object { - val KEY_CHARACTER_NAME = "KEY_CHARACTER_NAME" + const val KEY_CHARACTER_NAME = "KEY_CHARACTER_NAME" } + private var characterLiveData: LiveData<DndCharacter>? = null + + @OptIn(ExperimentalMaterialApi::class) override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) - characterViewModel = ViewModelProvider(this).get(CharacterViewModel::class.java) + characterViewModel = ViewModelProvider(this)[CharacterViewModel::class.java] val characterName = intent.getStringExtra(KEY_CHARACTER_NAME) - + val isCreateMode = characterName.isNullOrBlank() setContent { - var dndCharacter = characterName?.let { characterViewModel.get(it).observeAsState(DndCharacter()).value } ?: DndCharacter() - val editMode = dndCharacter.name.isBlank() - MyApp { - CreateCharacterScreenContent( - editMode, - character = dndCharacter, - onChangeDndCharacter = { dndCharacter = it } - ) + var dndCharacter: DndCharacter? by remember { mutableStateOf(null)} + characterLiveData = characterName?.let { characterViewModel.get(it) } + val originalCharacter = characterLiveData?.observeAsState() + + if (dndCharacter == null) + dndCharacter = if (!isCreateMode && originalCharacter != null) { + originalCharacter.value + } else { + DndCharacter() + } + + if (dndCharacter == null) + Column( + horizontalAlignment = Alignment.CenterHorizontally, + modifier = Modifier.fillMaxWidth() + ) { + CircularProgressIndicator() + } + else + CreateCharacterScreenContent( + isCreateMode, + character = dndCharacter!!, + onChangeDndCharacter = { dndCharacter = it } + ) } } } + + fun updateCharacter(character: DndCharacter) { + characterLiveData?.removeObservers(this) + characterViewModel.update(character) + } + + fun deleteCharacter(character: DndCharacter) { + characterLiveData?.removeObservers(this) + characterViewModel.delete(character) + finish() + } } @ExperimentalMaterialApi @@ -70,32 +99,40 @@ class CreateCharacterActivity : ComponentActivity() { fun CreateCharacterScreenContent( isCreateMode: Boolean = true, character: DndCharacter = DndCharacter(), - onChangeDndCharacter: (DndCharacter) -> Unit = {} + onChangeDndCharacter: (DndCharacter) -> Unit = {}, ) { val scope = rememberCoroutineScope() val scaffoldState = rememberScaffoldState() - val activity = (LocalContext.current as? Activity) + val activity = LocalContext.current as? CreateCharacterActivity - val topText: String = when (isCreateMode) { + val topText = when (isCreateMode) { true -> "Create Your Character" false -> "Modify Your Character" } - Scaffold( scaffoldState = scaffoldState, modifier = Modifier.fillMaxSize(), topBar = { - DndTopBar(topText) + DndTopBar( + topText, + actions = { + if (!isCreateMode) { + IconButton(onClick = { activity?.deleteCharacter(character) }) { + Icon(Icons.Outlined.Delete, "delet character") + } + } + } + ) }, content = { Column { CharacterDetailList( dndCharacter = character, onChangeDndCharacter = { - onChangeDndCharacter(it) - } + onChangeDndCharacter(it.copy()) + }, ) } }, @@ -116,56 +153,56 @@ fun CreateCharacterScreenContent( ) } } - - ) } @Composable -fun EditCharacterFloatingActionButton(dndCharacter: DndCharacter, activity: Activity?, scope: CoroutineScope, scaffoldState: ScaffoldState) { +fun EditCharacterFloatingActionButton( + dndCharacter: DndCharacter, + activity: CreateCharacterActivity?, + scope: CoroutineScope, + scaffoldState: ScaffoldState +) { val characterErrorText = stringResource(R.string.character_error) ExtendedFloatingActionButton( - text = { - Text(stringResource(R.string.modify_character)) - }, + text = { Text(stringResource(R.string.modify_character)) }, onClick = { val validation = validateCharacter(dndCharacter) if (validation){ - updateCharacter(dndCharacter) + activity?.updateCharacter(dndCharacter) activity?.finish() - } + } else scope.launch { scaffoldState.snackbarHostState.showSnackbar(characterErrorText) } }, - icon = { - Icon(Icons.Outlined.Edit, contentDescription = null) - } + icon = { Icon(Icons.Outlined.Edit, contentDescription = null) }, ) } @Composable -fun CreateCharacterFloatingActionButton(dndCharacter: DndCharacter, activity: Activity?, scope: CoroutineScope, scaffoldState: ScaffoldState) { +fun CreateCharacterFloatingActionButton( + dndCharacter: DndCharacter, + activity: Activity?, + scope: CoroutineScope, + scaffoldState: ScaffoldState +) { val characterErrorText = stringResource(R.string.character_error) ExtendedFloatingActionButton( - text = { - Text(stringResource(R.string.add_new_character)) - }, + text = { Text(stringResource(R.string.add_new_character)) }, onClick = { val validation = validateCharacter(dndCharacter) if (validation){ addNewCharacter(dndCharacter) activity?.finish() - } + } else scope.launch { scaffoldState.snackbarHostState.showSnackbar(characterErrorText) } }, - icon = { - Icon(Icons.Outlined.Add, contentDescription = null) - } + icon = { Icon(Icons.Outlined.Add, contentDescription = null) } ) } @@ -174,21 +211,11 @@ fun validateCharacter(dndCharacter: DndCharacter): Boolean { if (dndCharacter.name.isEmpty()) return false - if (dndCharacter.dndClass == DndCharacter.DndClass.None) + if (dndCharacter.dndClass == DndClass.None) return false if (dndCharacter.level > 20 || dndCharacter.level < 0) return false - // - val subclassCasters = listOf( - DndCharacter.DndClass.ArcaneTrickster, - DndCharacter.DndClass.EldritchKnight, - DndCharacter.DndClass.Ranger - ) - - if (subclassCasters.contains(dndCharacter.dndClass) && dndCharacter.level < 3) - return false - return true } @@ -199,19 +226,13 @@ fun CharacterDetailList( dndCharacter: DndCharacter, onChangeDndCharacter: (DndCharacter) -> Unit ) { - val ddoptions = DndCharacter.DndClass.values().toList().subList(0, 11) - - var characterClass by remember { mutableStateOf(dndCharacter.dndClass)} - var characterLevel by remember { mutableStateOf(dndCharacter.level) } - - var level by remember { mutableStateOf(dndCharacter.level) } + val classList = DndClass.values().toList().subList(0, 11) Column { OutlinedTextField( value = dndCharacter.name, onValueChange = { - dndCharacter.name = it - onChangeDndCharacter(dndCharacter) + onChangeDndCharacter(dndCharacter.copy(name = it)) }, modifier = modifier .fillMaxWidth() @@ -222,127 +243,26 @@ fun CharacterDetailList( modifier .fillMaxWidth() .padding(top = 10.dp, start = 25.dp, end = 25.dp, bottom = 15.dp), - ddoptions = ddoptions, + allClasses = classList, onClassChange = { - dndCharacter.dndClass = it - onChangeDndCharacter(dndCharacter) + onChangeDndCharacter(dndCharacter.copy(dndClass = it)) }, starterClass = dndCharacter.dndClass ) - LevelSlider( + LevelSelector( modifier = modifier .fillMaxWidth() .padding(horizontal = 25.dp, vertical = 0.dp), - level = characterLevel, + level = dndCharacter.level, onLevelChange = { - characterLevel = it - dndCharacter.level = it - onChangeDndCharacter(dndCharacter) + onChangeDndCharacter(dndCharacter.copy(level = it)) }, ) } } -@Composable -fun LevelSlider( - modifier: Modifier, - level: Int, - onLevelChange: (Int) -> Unit, -) { - Row( - horizontalArrangement = Arrangement.SpaceBetween, - modifier = modifier - .padding(start = 5.dp, top = 5.dp, end = 5.dp) - ) { - Text( - text = stringResource(id = R.string.character_level), - style = MaterialTheme.typography.body1 - ) - Text( - text = level.toString(), - style = MaterialTheme.typography.body1 - ) - } - LevelSlider { - onLevelChange(it) - } -} - -@Composable -fun LevelSlider(onValueChange: (Int) -> Unit ) { - var sliderPosition by remember { mutableStateOf(0f) } - - Slider( - value = sliderPosition, - onValueChange = { - sliderPosition = it - onValueChange((sliderPosition * 20f ).toInt()) - }, - modifier = Modifier - .padding(horizontal = 35.dp) - ) -} - - -@ExperimentalMaterialApi -@Composable -fun ClassSelector( - modifier: Modifier, - ddoptions: List<DndCharacter.DndClass>, - onClassChange: (DndCharacter.DndClass) -> Unit, - starterClass: DndCharacter.DndClass -) { - var expandedState by remember { mutableStateOf(false) } - var selectedOption by remember { mutableStateOf(starterClass) } - - ExposedDropdownMenuBox( - expanded = expandedState, - onExpandedChange = { - expandedState = !expandedState - }, - modifier = modifier - - ) { - OutlinedTextField( - readOnly = true, - value = selectedOption.legibleName, - onValueChange = {}, - label = { Text("Class") }, - trailingIcon = { - ExposedDropdownMenuDefaults.TrailingIcon( - expanded = expandedState - ) - }, - modifier = Modifier.fillMaxWidth() - ) - - ExposedDropdownMenu( - expanded = expandedState, - onDismissRequest = { - expandedState = false - }, -// modifier = Modifier -// .fillMaxWidth(), - ) { - - ddoptions.forEach { - DropdownMenuItem( - onClick = { - onClassChange(it) - selectedOption = it - expandedState = false - }, - modifier = Modifier.fillMaxWidth() - ) { - Text(text = it.legibleName) - } - } - } - } -} - @Composable fun MyApp(component: @Composable () -> Unit) { DndSpellsTheme { @@ -353,48 +273,24 @@ fun MyApp(component: @Composable () -> Unit) { } } +@ExperimentalMaterialApi +@Preview(showBackground = true) @Composable -fun Title( - titleText: String, - modifier: Modifier = Modifier -) { - Text( - text = titleText, - fontSize = MaterialTheme.typography.h4.fontSize, - modifier = modifier - .fillMaxWidth(), - textAlign = TextAlign.Center - ) -} - -@Composable -fun DndTopBar(titleText: String? = null) { - val activity = (LocalContext.current as? Activity) - - TopAppBar( - title = { - Text( - text = titleText?:stringResource(id = R.string.app_name) - ) - }, - elevation = 0.dp, - backgroundColor = MaterialTheme.colors.primary, - navigationIcon = { - IconButton(onClick = { activity?.onBackPressed() }) { - Icon( - Icons.Outlined.ArrowBack, - "" - ) - } +fun CreateCharacterPreview() { + DndSpellsTheme { + Surface { + CreateCharacterScreenContent() } - ) + } } @ExperimentalMaterialApi @Preview(showBackground = true) @Composable -fun CreateCharacterPreview() { - MyApp { - CreateCharacterScreenContent() +fun CreateCharacterDarkPreview() { + DndSpellsTheme(darkTheme = true) { + Surface(color = MaterialTheme.colors.background) { + CreateCharacterScreenContent() + } } } \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/MainActivity.kt b/app/src/main/java/com/flyinpancake/dndspells/MainActivity.kt index a0d05446a67de70441a125458203303373c66271..6051f0e79d12412bd422408f547a4e9016ab9f9a 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/MainActivity.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/MainActivity.kt @@ -49,9 +49,9 @@ class MainActivity : AppCompatActivity(), MainMenuRecyclerViewAdapter.SpellListI setContentView(binding.root) setSupportActionBar(binding.toolbar) - binding.toolbar.title = title +// binding.toolbar.title = title - characterViewModel = ViewModelProvider(this).get(CharacterViewModel::class.java) + characterViewModel = ViewModelProvider(this)[CharacterViewModel::class.java] characterViewModel.allCharacters.observe(this ,{ characters -> recyclerViewAdapter.submitList(characters) }) @@ -69,21 +69,13 @@ class MainActivity : AppCompatActivity(), MainMenuRecyclerViewAdapter.SpellListI override fun onItemClick(character: DndCharacter, binding: RecyclerviewMainMenuRowBinding) { val intent = Intent(this, CharacterDetailsActivity::class.java) - intent.putExtra(ProfileActivity.KEY_NAME, character.name) - - val option = ActivityOptionsCompat.makeSceneTransitionAnimation( - this, - binding.tvCharacterName, - "character_name" - ) - startActivity(intent, option.toBundle()) + intent.putExtra(CharacterDetailsActivity.KEY_NAME, character.name) + startActivity(intent) } - @OptIn(ExperimentalMaterialApi::class) override fun onItemLongClick(character: DndCharacter, binding: RecyclerviewMainMenuRowBinding) { val intent = Intent(this, CreateCharacterActivity::class.java) intent.putExtra(CreateCharacterActivity.KEY_CHARACTER_NAME, character.name) - startActivity(intent) } @@ -92,8 +84,6 @@ class MainActivity : AppCompatActivity(), MainMenuRecyclerViewAdapter.SpellListI return super.onCreateOptionsMenu(menu) } - - @OptIn(ExperimentalMaterialApi::class) override fun onOptionsItemSelected(item: MenuItem): Boolean { when (item.itemId) { R.id.import_xml -> { diff --git a/app/src/main/java/com/flyinpancake/dndspells/ProfileActivity.kt b/app/src/main/java/com/flyinpancake/dndspells/ProfileActivity.kt deleted file mode 100644 index a1520c2248c788a8cbf2bdb2748d80fba9bcda44..0000000000000000000000000000000000000000 --- a/app/src/main/java/com/flyinpancake/dndspells/ProfileActivity.kt +++ /dev/null @@ -1,47 +0,0 @@ -package com.flyinpancake.dndspells - -import android.os.Bundle -import androidx.appcompat.app.AppCompatActivity -import androidx.lifecycle.ViewModelProvider -import androidx.recyclerview.widget.LinearLayoutManager -import com.flyinpancake.dndspells.adapter.ProfileSpellRecyclerViewAdapter -import com.flyinpancake.dndspells.databinding.ActivityProfileBinding -import com.flyinpancake.dndspells.databinding.RecyclerviewSpellRowBinding -import com.flyinpancake.dndspells.model.Spell -import com.flyinpancake.dndspells.viewmodel.SpellViewModel - -class ProfileActivity : AppCompatActivity(), ProfileSpellRecyclerViewAdapter.SpellListItemClickListener { - companion object { - const val KEY_NAME = "KEY_NAME" - } - private lateinit var binding : ActivityProfileBinding - private lateinit var spellListViewModel : SpellViewModel - private val recyclerViewAdapter = ProfileSpellRecyclerViewAdapter() - override fun onCreate(savedInstanceState: Bundle?) { - binding = ActivityProfileBinding.inflate(this.layoutInflater) - super.onCreate(savedInstanceState) - setContentView(binding.root) - binding.tvCharacterName.text = intent.getStringExtra(KEY_NAME)!! - - spellListViewModel = ViewModelProvider(this).get(SpellViewModel::class.java) - recyclerViewAdapter.itemClickListener = this - - setupSpellList() - } - - - - private fun setupSpellList() { - spellListViewModel.allSpells.observe(this,{ spells -> - recyclerViewAdapter.submitList(spells) - }) - binding.rvSpellList.adapter = recyclerViewAdapter - binding.rvSpellList.layoutManager = LinearLayoutManager(this) - } - - override fun onItemClick(spell: Spell, binding: RecyclerviewSpellRowBinding) { -// val intent = Intent(this, SpellDetailsActivity::class.java) -// intent.putExtra(SpellDetailsActivity.KEY_SPELLNAME, Json.encodeToString(spell)) -// startActivity(intent) - } -} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/SelectSpellsActivity.kt b/app/src/main/java/com/flyinpancake/dndspells/SelectSpellsActivity.kt index 5de552b501d27a333effdb5d5467396603a761c4..3798ac63500fe4eb6bcb0bc3f5f8561af6e9af29 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/SelectSpellsActivity.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/SelectSpellsActivity.kt @@ -7,8 +7,11 @@ import androidx.compose.foundation.layout.* import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.foundation.lazy.items import androidx.compose.material.* +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.outlined.Info import androidx.compose.runtime.* import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.res.stringResource import androidx.compose.ui.text.style.TextOverflow @@ -17,10 +20,16 @@ import androidx.compose.ui.unit.dp import androidx.lifecycle.ViewModelProvider import com.flyinpancake.dndspells.CharacterDetailsActivity.Companion.KEY_NAME import com.flyinpancake.dndspells.model.DndCharacter +import com.flyinpancake.dndspells.model.DndClass import com.flyinpancake.dndspells.model.Spell +import com.flyinpancake.dndspells.ui.components.DndTopBar +import com.flyinpancake.dndspells.ui.components.SpellContent +import com.flyinpancake.dndspells.ui.components.SpellFilterComponent +import com.flyinpancake.dndspells.ui.logic.SpellFilter import com.flyinpancake.dndspells.ui.theme.DndSpellsTheme import com.flyinpancake.dndspells.viewmodel.CharacterViewModel import com.flyinpancake.dndspells.viewmodel.SpellViewModel +import kotlinx.coroutines.launch class SelectSpellsActivity : ComponentActivity() { @@ -45,38 +54,73 @@ class SelectSpellsActivity : ComponentActivity() { } } +@OptIn(ExperimentalMaterialApi::class) @Composable fun SelectSpellsContent( spells: List<Spell>, character: DndCharacter, updateCharacter: (DndCharacter) -> Unit = {} ) { - Scaffold( - topBar = { DndTopBar(character.name + stringResource(R.string.select_spells)) } + val scope = rememberCoroutineScope() + val scaffoldState = rememberBottomSheetScaffoldState() + + var spellFilter by remember { mutableStateOf(SpellFilter(classFilter = character.dndClass)) } + + BottomSheetScaffold( + topBar = { DndTopBar(character.name + " " + stringResource(R.string.select_spells)) }, + sheetPeekHeight = 64.dp, + sheetContent = { + Box( + Modifier + .fillMaxWidth() + .height(64.dp), + contentAlignment = Alignment.Center + ) { + Column { + Text( + text = "Swipe to Filter Spells", + style = MaterialTheme.typography.body1 + ) + } + } + + SpellFilterComponent( + spellFilter = spellFilter, + onSpellFilterChanged = {spellFilter = it} + ) + }, + scaffoldState = scaffoldState, + floatingActionButton = { + FloatingActionButton(onClick = { + scope.launch { + if (scaffoldState.bottomSheetState.isCollapsed) + scaffoldState.bottomSheetState.expand() + else if (scaffoldState.bottomSheetState.isExpanded) + scaffoldState.bottomSheetState.collapse() + } + }) { + Icon(Icons.Outlined.Info, "filter") + } + } ) { LazyColumn { items( - items = spells.toList(), + items = spellFilter.filterSpells(spells), itemContent = { spell -> - var selectedState by remember { mutableStateOf( character.spellList.contains(spell.name)) } SpellCardWithCheckBox( spell = spell, - checked = selectedState, + checked = character.spellList.contains(spell.name), onCheck = { newContains -> val newSpellList = character.spellList.toMutableList() if (newContains && !newSpellList.contains(spell.name)) { newSpellList.add(spell.name) - } else if (newSpellList.contains(spell.name)){ + } else if (newSpellList.contains(spell.name)) { newSpellList.remove(spell.name) } - selectedState = !selectedState - character.spellList = newSpellList - updateCharacter(character) + updateCharacter(character.copy(spellList = newSpellList)) }) }) } - - } } @@ -95,8 +139,7 @@ private fun SpellCardWithCheckBox( Modifier .fillMaxSize() .padding(10.dp), - - ) { + ) { Checkbox( checked = checked, onCheckedChange = { onCheck(it) }, @@ -107,54 +150,7 @@ private fun SpellCardWithCheckBox( } } -@Composable -fun SpellContent(spell: Spell) { - val textPadding = Modifier.padding(horizontal = 5.dp) - Column( - Modifier.fillMaxSize(), - verticalArrangement = Arrangement.Center, - ) { - Row( - Modifier.fillMaxSize(), - horizontalArrangement = Arrangement.SpaceBetween - ) { - Text( - text = spell.name, - modifier = textPadding, - maxLines = 1, - overflow = TextOverflow.Ellipsis, - style = MaterialTheme.typography.h6 - ) - Text( - text = "Level ${spell.level}", - modifier = textPadding, - maxLines = 1, - style = MaterialTheme.typography.h6 - ) - } - Row( - Modifier.fillMaxSize(), - horizontalArrangement = Arrangement.SpaceBetween - ) { - Text(text = spell.range, modifier = textPadding, style = MaterialTheme.typography.body1) - Text(text = spell.time, modifier = textPadding, style = MaterialTheme.typography.body1) - Text( - text = spell.components, - style = MaterialTheme.typography.body1, - modifier = textPadding, - maxLines = 1, - overflow = TextOverflow.Ellipsis - ) - } - } -} - -@Composable -private fun SelectableSpellList(spells: List<Spell>, character: DndCharacter) { - -} - -val samplespells = listOf( +val sampleSpells = listOf( Spell( name = "Power Word Kill", level = 9, @@ -165,31 +161,32 @@ val samplespells = listOf( range = "240 ft", ritual = false, school = "E", - time = "instantanius" + time = "instantaneous", + roll = "10d6" ) ) val sampleCharacter = DndCharacter( name = "Ba'luk", level = 4, - dndClass = DndCharacter.DndClass.Druid, + dndClass = DndClass.Druid, spellList = listOf("Power Word Kill") ) @Preview(showBackground = true) @Composable -fun DefaultPreview() { +fun SpellSelectPreview() { DndSpellsTheme { - SelectSpellsContent(spells = samplespells, character = sampleCharacter) + SelectSpellsContent(spells = sampleSpells, character = sampleCharacter) } } @Preview(showBackground = true) @Composable -fun DefaultDarkPreview() { +fun SpellSelectDarkPreview() { - DndSpellsTheme (darkTheme = true) { - SelectSpellsContent(spells = samplespells, character = sampleCharacter) + DndSpellsTheme(darkTheme = true) { + SelectSpellsContent(spells = sampleSpells, character = sampleCharacter) } } diff --git a/app/src/main/java/com/flyinpancake/dndspells/SpellDetailsActivity.kt b/app/src/main/java/com/flyinpancake/dndspells/SpellDetailsActivity.kt index 492c7599c1f73a8899d7511e54b29585c80a3ba7..2ef10fdfbf0e7c00b4c71e1622331809b8229af3 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/SpellDetailsActivity.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/SpellDetailsActivity.kt @@ -3,74 +3,89 @@ package com.flyinpancake.dndspells import android.os.Bundle import androidx.activity.ComponentActivity import androidx.activity.compose.setContent -import androidx.compose.foundation.gestures.scrollable import androidx.compose.foundation.layout.* import androidx.compose.foundation.rememberScrollState import androidx.compose.foundation.verticalScroll -import androidx.compose.material.MaterialTheme -import androidx.compose.material.Scaffold -import androidx.compose.material.Surface -import androidx.compose.material.Text +import androidx.compose.material.* import androidx.compose.runtime.Composable +import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.runtime.rememberCoroutineScope import androidx.compose.ui.Modifier +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.res.stringResource import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp import androidx.lifecycle.ViewModelProvider import com.flyinpancake.dndspells.model.Spell +import com.flyinpancake.dndspells.ui.components.DndTopBar import com.flyinpancake.dndspells.ui.theme.DndSpellsTheme import com.flyinpancake.dndspells.viewmodel.SpellViewModel +import kotlinx.coroutines.launch import kotlinx.serialization.ExperimentalSerializationApi -import kotlinx.serialization.decodeFromString -import kotlinx.serialization.json.Json - -lateinit var spellViewModel: SpellViewModel class SpellDetailsActivity : ComponentActivity() { - private lateinit var spell: Spell - companion object{ - val KEY_SPELLNAME = "KEY_SPELLNAME" + const val KEY_SPELL_NAME = "KEY_SPELL_NAME" } + @OptIn(ExperimentalSerializationApi::class) override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) - val spellJson = intent.getStringExtra(KEY_SPELLNAME)?: "" - spell = Json.decodeFromString(spellJson) - + val spellName = intent.getStringExtra(KEY_SPELL_NAME)?: "" setContent { + val spell = ViewModelProvider(this)[SpellViewModel::class.java] + .get(spellName) + .observeAsState(Spell()) + .value + DndSpellsTheme { // A surface container using the 'background' color from the theme Surface(color = MaterialTheme.colors.background) { - SpellDetails(spell) + SpellDetails(spell = spell) } } } } } - - @Composable -fun SpellDetails(spell: Spell) { +fun SpellDetails( + spell: Spell, +) { + val scope = rememberCoroutineScope() + val scaffoldState = rememberScaffoldState() + + val youRolled = stringResource(id = R.string.you_rolled) Scaffold( modifier = Modifier .fillMaxSize(), - topBar = { DndTopBar() } - ) { + topBar = { DndTopBar(spell.name) }, + floatingActionButton = { + spell.roll?.let { roll -> + ExtendedFloatingActionButton( + text = { Text("Cast Spell") }, + onClick = { + scope.launch { + scaffoldState.snackbarHostState.showSnackbar(youRolled + roll(roll.trim())) + } + }, + icon = { Icon(painterResource(id = R.drawable.dice_5_outline), null) } + ) + } + }, + scaffoldState = scaffoldState, + ) { Column( Modifier .verticalScroll(rememberScrollState()) ) { - Title(titleText = spell.name) SpellAttributes(spell) SpellDescription(spell) } - } - } @Composable @@ -107,7 +122,7 @@ fun SpellAttributes(spell: Spell) { @Composable fun SpellDescription(spell: Spell){ Text( - text = spell.desc, + text = spell.desc.replace("\n\t",""), modifier = Modifier .padding(25.dp) .fillMaxSize(), @@ -119,6 +134,6 @@ fun SpellDescription(spell: Spell){ @Composable fun DefaultPreview2() { DndSpellsTheme { -// SpellDetails() + SpellDetails(Spell()) } } \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/adapter/MainMenuRecyclerViewAdapter.kt b/app/src/main/java/com/flyinpancake/dndspells/adapter/MainMenuRecyclerViewAdapter.kt index c12a8449e2e92010881f666c82a2aa3a526bed69..7af0e55adcab21479d8b77c3c180aeb9b0d8c544 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/adapter/MainMenuRecyclerViewAdapter.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/adapter/MainMenuRecyclerViewAdapter.kt @@ -10,9 +10,9 @@ import com.flyinpancake.dndspells.databinding.RecyclerviewMainMenuRowBinding import com.flyinpancake.dndspells.model.DndCharacter class MainMenuRecyclerViewAdapter : - ListAdapter<DndCharacter, MainMenuRecyclerViewAdapter.MainMenuViewHolder>(itemCallback) { + ListAdapter<DndCharacter, MainMenuRecyclerViewAdapter.MainMenuViewHolder>(ItemCallback) { companion object { - object itemCallback: DiffUtil.ItemCallback<DndCharacter>() { + object ItemCallback: DiffUtil.ItemCallback<DndCharacter>() { override fun areItemsTheSame(oldItem: DndCharacter, newItem: DndCharacter): Boolean { return newItem == oldItem } @@ -57,4 +57,4 @@ class MainMenuRecyclerViewAdapter : override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = MainMenuViewHolder( RecyclerviewMainMenuRowBinding.inflate(LayoutInflater.from(parent.context), parent, false) ) -} \ No newline at end of file +} diff --git a/app/src/main/java/com/flyinpancake/dndspells/adapter/ProfileSpellRecyclerViewAdapter.kt b/app/src/main/java/com/flyinpancake/dndspells/adapter/ProfileSpellRecyclerViewAdapter.kt deleted file mode 100644 index 5f92d1273ef4f7dac6100ed1248a73b0b46d89bc..0000000000000000000000000000000000000000 --- a/app/src/main/java/com/flyinpancake/dndspells/adapter/ProfileSpellRecyclerViewAdapter.kt +++ /dev/null @@ -1,57 +0,0 @@ -package com.flyinpancake.dndspells.adapter - -import android.os.Parcel -import android.os.Parcelable -import android.view.LayoutInflater -import android.view.ViewGroup -import androidx.recyclerview.widget.DiffUtil -import androidx.recyclerview.widget.ListAdapter -import androidx.recyclerview.widget.RecyclerView -import com.flyinpancake.dndspells.model.Spell -import com.flyinpancake.dndspells.databinding.RecyclerviewSpellRowBinding - -class ProfileSpellRecyclerViewAdapter : ListAdapter<Spell, ProfileSpellRecyclerViewAdapter.ViewHolder>(itemCallback) { - - companion object { - object itemCallback: DiffUtil.ItemCallback<Spell>() { - override fun areItemsTheSame(oldItem: Spell, newItem: Spell): Boolean { - return oldItem == newItem - } - - override fun areContentsTheSame(oldItem: Spell, newItem: Spell): Boolean { - return newItem.name == oldItem.name - } - } - } - - inner class ViewHolder(val binding: RecyclerviewSpellRowBinding) : - RecyclerView.ViewHolder(binding.root) { - var spell: Spell? = null - - init { - itemView.setOnClickListener { - spell?.let { spell -> itemClickListener?.onItemClick(spell, binding) } - } - } - } - - override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder( - RecyclerviewSpellRowBinding.inflate(LayoutInflater.from(parent.context), parent, false) - ) - - override fun onBindViewHolder(holder: ViewHolder, position: Int) { - val spell = this.getItem(position) - - holder.binding.SpellComponents.text = spell.components - holder.binding.SpellLevel.text = "${spell.level}" - holder.binding.SpellSchool.text = spell.school - holder.binding.tvSpellName.text = spell.name - holder.spell = spell - } - - var itemClickListener: SpellListItemClickListener? = null - - interface SpellListItemClickListener { - fun onItemClick(spell: Spell, binding: RecyclerviewSpellRowBinding) - } -} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDao.kt b/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDao.kt index 0d78df4726409775c9c92400e699a9173bd99e2b..2d970acf207a66e03b52b3ba7a3b428c2bef870b 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDao.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDao.kt @@ -11,6 +11,9 @@ interface CharacterDao { @Query("SELECT * FROM characters") fun getAllCharacters(): LiveData<List<RoomCharacter>> + @Query("SELECT * FROM characters WHERE id == :id") + fun getCharacter(id: Int): RoomCharacter? + @Query("SELECT * FROM characters WHERE name == :name") fun getCharacterByName(name: String): RoomCharacter? @@ -24,6 +27,4 @@ interface CharacterDao { fun deleteCharacter( character: RoomCharacter ) - - -} \ No newline at end of file +} diff --git a/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDatabase.kt b/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDatabase.kt index 7c419e3a86dfedbe03fd99390299f5c3a4a0a62d..6858ee5966a7240b590060f887e4cbaaba08ce03 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDatabase.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/database/CharacterDatabase.kt @@ -10,4 +10,4 @@ import androidx.room.RoomDatabase ) abstract class CharacterDatabase : RoomDatabase() { abstract fun characterDao(): CharacterDao -} \ No newline at end of file +} diff --git a/app/src/main/java/com/flyinpancake/dndspells/database/RoomCharacter.kt b/app/src/main/java/com/flyinpancake/dndspells/database/RoomCharacter.kt index fdcb1e83d010dd771fe0065c3ed34851e93e1327..4ec8df730ba004ed89deaf7d0e4f30315494edee 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/database/RoomCharacter.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/database/RoomCharacter.kt @@ -1,15 +1,14 @@ package com.flyinpancake.dndspells.database import androidx.room.Entity -import androidx.room.Index import androidx.room.PrimaryKey -@Entity(tableName = "characters", indices = [Index(value = ["name"], unique = true)]) +@Entity(tableName = "characters") class RoomCharacter( @PrimaryKey(autoGenerate = true) val id: Int = 0, - var name: String, - var level: Int, - var dndClass: String, + val name: String, + val level: Int, + val dndClass: String, val spellNameList: String, ) \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/database/RoomSpell.kt b/app/src/main/java/com/flyinpancake/dndspells/database/RoomSpell.kt index 89320472b4b62af3e60e4d9bc509976bf4b7271b..d9fe258ddb4c8135022eee5f61982fe4abc91efd 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/database/RoomSpell.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/database/RoomSpell.kt @@ -19,4 +19,5 @@ data class RoomSpell( val ritual: Boolean, val duration: String, val classes: String, + val roll: String? ) \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/database/SpellDao.kt b/app/src/main/java/com/flyinpancake/dndspells/database/SpellDao.kt index 3e1804194075543c760ae6f725d2691be347f545..67c4df154dfbf03d755d756081929d0e03e2bb6e 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/database/SpellDao.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/database/SpellDao.kt @@ -18,6 +18,9 @@ interface SpellDao { @Query("SELECT * FROM spells WHERE name == :name") fun getSpellByName(name: String): RoomSpell? + @Query("SELECT * FROM spells WHERE name == :name") + fun getSpellLiveByName(name: String): LiveData<RoomSpell> + @Delete fun deleteSpell(spell: RoomSpell) diff --git a/app/src/main/java/com/flyinpancake/dndspells/database/SpellDatabase.kt b/app/src/main/java/com/flyinpancake/dndspells/database/SpellDatabase.kt index b20de39c775cf2bf38c78e24151039b92afe7575..b834f43166c270cf4570539f65b0d827a4f008e3 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/database/SpellDatabase.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/database/SpellDatabase.kt @@ -2,8 +2,6 @@ package com.flyinpancake.dndspells.database import androidx.room.Database import androidx.room.RoomDatabase -import androidx.room.TypeConverters - @Database( version = 1, diff --git a/app/src/main/java/com/flyinpancake/dndspells/model/DndCharacter.kt b/app/src/main/java/com/flyinpancake/dndspells/model/DndCharacter.kt index 05f6a41903dc051218067d3f8d82257136374834..de16a896d9ea1a7db0691f7477c73c84d210cfba 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/model/DndCharacter.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/model/DndCharacter.kt @@ -1,31 +1,18 @@ package com.flyinpancake.dndspells.model data class DndCharacter( - var id: Int = 0, - var name: String, - var level: Int, - var dndClass: DndClass, - var spellList: List<String>, + val id: Int = 0, + val name: String, + val level: Int, + val dndClass: DndClass, + val spellList: List<String>, ) { constructor() :this(name = "" , level = 0, dndClass = DndClass.None, spellList = listOf()) constructor(name: String, level: Int, dndClass: DndClass) :this(name = name, level = level, dndClass = dndClass, spellList = listOf()) - enum class DndClass(val legibleName: String) { - - - ArcaneTrickster("Rouge (Arcane Trickster)"), - Artificer("Artificer"), - Bard("Bard"), - Cleric("Cleric"), - Druid("Druid"), - EldritchKnight("Fighter (Eldritch Knight)"), - Paladin("Paladin"), - Ranger("Ranger"), - Sorcerer("Sorcerer"), - Warlock("Warlock"), - Wizard("Wizard"), - None("None"),; + override fun toString(): String { + return "${name}, level:${level}, class:${dndClass.legibleName}" } } diff --git a/app/src/main/java/com/flyinpancake/dndspells/model/DndClass.kt b/app/src/main/java/com/flyinpancake/dndspells/model/DndClass.kt new file mode 100644 index 0000000000000000000000000000000000000000..f2283cdd7cbe6cfe2f5f4ffcffe2688497bcad3d --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/model/DndClass.kt @@ -0,0 +1,16 @@ +package com.flyinpancake.dndspells.model + +enum class DndClass(val legibleName: String) { + Artificer("Artificer"), + Bard("Bard"), + Cleric("Cleric"), + Druid("Druid"), + Fighter("Fighter"), + Paladin("Paladin"), + Ranger("Ranger"), + Rouge("Rouge"), + Sorcerer("Sorcerer"), + Warlock("Warlock"), + Wizard("Wizard"), + None("None"),; +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/model/DndSubclass.kt b/app/src/main/java/com/flyinpancake/dndspells/model/DndSubclass.kt new file mode 100644 index 0000000000000000000000000000000000000000..9ea0484fa261dd0a31a1562ef10e8e7370dc71c8 --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/model/DndSubclass.kt @@ -0,0 +1,4 @@ +package com.flyinpancake.dndspells.model + +class DndSubclass { +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/model/Spell.kt b/app/src/main/java/com/flyinpancake/dndspells/model/Spell.kt index c7521a7457cace575bc5968c8a2c77eec1337277..c0d350436af62b64314a4a3f0c49590000f1b8bc 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/model/Spell.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/model/Spell.kt @@ -14,4 +14,19 @@ data class Spell ( val ritual: Boolean, val duration: String, val classes: String, -) + val roll: String? +) { + constructor() : this( + name = "", + desc = "", + level = 0, + components = "", + range = "", + time = "", + school = "", + ritual = false, + duration = "", + classes = "", + roll = null + ) +} diff --git a/app/src/main/java/com/flyinpancake/dndspells/model/SpellImporter.kt b/app/src/main/java/com/flyinpancake/dndspells/model/SpellImporter.kt index 77d940a2509ea6446858cd768428f5f626ca89b7..a4c9150cd28d69322635858c984e6a9d6d600c13 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/model/SpellImporter.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/model/SpellImporter.kt @@ -65,6 +65,7 @@ class SpellImporter { var ritual: Boolean? = null var duration: String? = null var classes: String? = null + var roll: String? = null while (parser.next() != XmlPullParser.END_TAG) { @@ -81,6 +82,7 @@ class SpellImporter { "duration" -> duration = readDuration(parser) "classes" -> classes = readClasses(parser) "text" -> desc += readText(parser) + "roll" -> roll = readRoll(parser) else -> skip(parser) } } @@ -97,7 +99,8 @@ class SpellImporter { school ?: "", ritual ?: false, duration ?: "", - classes?: "Any" + classes?: "Any", + roll ) } @@ -114,6 +117,11 @@ class SpellImporter { return readInsideTags(parser, "classes") } + @Throws(IOException::class, XmlPullParserException::class) + private fun readRoll(parser: XmlPullParser): String { + return readInsideTags(parser, "roll") + } + @Throws(IOException::class, XmlPullParserException::class) private fun readText(parser: XmlPullParser): String { var text = readInsideTags(parser, "text") diff --git a/app/src/main/java/com/flyinpancake/dndspells/repository/CharacterRepository.kt b/app/src/main/java/com/flyinpancake/dndspells/repository/CharacterRepository.kt index 34ba87746f9b6b623b6ce6d05eb01e416b178403..300df0bc43a189d6ff7874431de065ef86b45fea 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/repository/CharacterRepository.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/repository/CharacterRepository.kt @@ -2,10 +2,10 @@ package com.flyinpancake.dndspells.repository import androidx.lifecycle.LiveData import androidx.lifecycle.map -import com.flyinpancake.dndspells.DndApplication import com.flyinpancake.dndspells.database.CharacterDao import com.flyinpancake.dndspells.database.RoomCharacter import com.flyinpancake.dndspells.model.DndCharacter +import com.flyinpancake.dndspells.model.DndClass import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.withContext @@ -24,7 +24,7 @@ class CharacterRepository( } suspend fun delete(character: DndCharacter) = withContext(Dispatchers.IO) { - val roomCharacter = characterDao.getCharacterByName(character.name) + val roomCharacter = characterDao.getCharacter(character.id) roomCharacter?.let { characterDao.deleteCharacter(roomCharacter) } } @@ -55,16 +55,17 @@ private fun DndCharacter.toRoomDomain(): RoomCharacter { } private fun RoomCharacter.toDomainModel(): DndCharacter { - val dndCharacter = DndCharacter() - dndCharacter.name = name - dndCharacter.level = level - dndCharacter.id = id - if (spellNameList.isNotEmpty()) - dndCharacter.spellList = spellNameList.split('\n') - DndCharacter.DndClass.values().forEach { dndClass -> - if (dndClass.legibleName == this.dndClass) - dndCharacter.dndClass = dndClass + var characterClass: DndClass = DndClass.None + DndClass.values().forEach { + if (it.legibleName == dndClass){ + characterClass = it + } } - - return dndCharacter + return DndCharacter( + name = name, + level = level, + id = id, + spellList = spellNameList.split('\n'), + dndClass = characterClass + ) } diff --git a/app/src/main/java/com/flyinpancake/dndspells/repository/SpellRepository.kt b/app/src/main/java/com/flyinpancake/dndspells/repository/SpellRepository.kt index a87c181a60350ea3b7a06ed14fc96b583b50f946..4c4eea9a7360f979d0ed5a6d5d50d8c529e544f9 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/repository/SpellRepository.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/repository/SpellRepository.kt @@ -29,6 +29,10 @@ class SpellRepository(private val spellDao: SpellDao) { spellDao.nukeSpells() } + fun getSpellByName(spellName: String): LiveData<Spell> { + return spellDao.getSpellLiveByName(spellName).map { it.toDomainModel() } + } + } @@ -43,13 +47,14 @@ private fun Spell.toRoomModel(): RoomSpell { range = range, ritual = ritual, school = school, - time = time + time = time, + roll = roll ) } fun RoomSpell.toDomainModel(): Spell { - return Spell(name, desc, level, components, range, time, school, ritual, duration, classes) + return Spell(name, desc, level, components, range, time, school, ritual, duration, classes, roll) } diff --git a/app/src/main/java/com/flyinpancake/dndspells/ui/components/ClassSelector.kt b/app/src/main/java/com/flyinpancake/dndspells/ui/components/ClassSelector.kt new file mode 100644 index 0000000000000000000000000000000000000000..ce0de67b087c200cc7498d4bd370813b83a6ca53 --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/ui/components/ClassSelector.kt @@ -0,0 +1,63 @@ +package com.flyinpancake.dndspells.ui.components + +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.material.* +import androidx.compose.runtime.* +import androidx.compose.ui.Modifier +import com.flyinpancake.dndspells.model.DndCharacter +import com.flyinpancake.dndspells.model.DndClass + +@ExperimentalMaterialApi +@Composable +fun ClassSelector( + modifier: Modifier, + allClasses: List<DndClass>, + onClassChange: (DndClass) -> Unit, + starterClass: DndClass +) { + var expandedState by remember { mutableStateOf(false) } + var selectedOption by remember { mutableStateOf(starterClass) } + + ExposedDropdownMenuBox( + expanded = expandedState, + onExpandedChange = { + expandedState = !expandedState + }, + modifier = modifier + + ) { + OutlinedTextField( + readOnly = true, + value = selectedOption.legibleName, + onValueChange = {}, + label = { Text("Class") }, + trailingIcon = { + ExposedDropdownMenuDefaults.TrailingIcon( + expanded = expandedState + ) + }, + modifier = Modifier.fillMaxWidth() + ) + + ExposedDropdownMenu( + expanded = expandedState, + onDismissRequest = { + expandedState = false + }, + ) { + + allClasses.forEach { + DropdownMenuItem( + onClick = { + onClassChange(it) + selectedOption = it + expandedState = false + }, + modifier = Modifier.fillMaxWidth() + ) { + Text(text = it.legibleName) + } + } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/ui/components/DndTopBar.kt b/app/src/main/java/com/flyinpancake/dndspells/ui/components/DndTopBar.kt new file mode 100644 index 0000000000000000000000000000000000000000..dd2e573726593fa7b310ac6694cab59093ed1c0d --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/ui/components/DndTopBar.kt @@ -0,0 +1,35 @@ +package com.flyinpancake.dndspells.ui.components + +import android.app.Activity +import androidx.compose.foundation.layout.RowScope +import androidx.compose.material.* +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.outlined.ArrowBack +import androidx.compose.runtime.Composable +import androidx.compose.ui.platform.LocalContext +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.unit.dp +import com.flyinpancake.dndspells.R + +@Composable +fun DndTopBar( + titleText: String? = null, + actions: @Composable RowScope.() -> Unit = {} +) { + val activity = (LocalContext.current as? Activity) + + TopAppBar( + title = { Text(text = titleText?: stringResource(id = R.string.app_name)) }, + elevation = 0.dp, + backgroundColor = MaterialTheme.colors.primary, + navigationIcon = { + IconButton(onClick = { activity?.onBackPressed() }) { + Icon( + imageVector = Icons.Outlined.ArrowBack, + contentDescription = "back arrow" + ) + } + }, + actions = actions, + ) +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/ui/components/LevelSelector.kt b/app/src/main/java/com/flyinpancake/dndspells/ui/components/LevelSelector.kt new file mode 100644 index 0000000000000000000000000000000000000000..4efd253231b0cc7109ca5c16580c4416661c93a5 --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/ui/components/LevelSelector.kt @@ -0,0 +1,53 @@ +package com.flyinpancake.dndspells.ui.components + +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.padding +import androidx.compose.material.MaterialTheme +import androidx.compose.material.Slider +import androidx.compose.material.Text +import androidx.compose.runtime.* +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.unit.dp +import com.flyinpancake.dndspells.R + +@Composable +fun LevelSelector( + modifier: Modifier, + level: Int, + onLevelChange: (Int) -> Unit, +) { + Row( + horizontalArrangement = Arrangement.SpaceBetween, + modifier = modifier + .padding(start = 5.dp, top = 5.dp, end = 5.dp) + ) { + Text( + text = stringResource(id = R.string.character_level), + style = MaterialTheme.typography.body1 + ) + Text(text = "$level", style = MaterialTheme.typography.body1) + } + LevelSlider (level) { + onLevelChange(it) + } +} + +@Composable +private fun LevelSlider( + starterValue: Int, + onValueChange: (Int) -> Unit +) { + var sliderPosition by remember { mutableStateOf(starterValue / 20f) } + + Slider( + value = sliderPosition, + onValueChange = { + sliderPosition = it + onValueChange((sliderPosition * 20f ).toInt()) + }, + modifier = Modifier + .padding(horizontal = 35.dp) + ) +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/ui/components/SpellContent.kt b/app/src/main/java/com/flyinpancake/dndspells/ui/components/SpellContent.kt new file mode 100644 index 0000000000000000000000000000000000000000..82edc0cc054abf3697104b22b3a4e491d5376ba2 --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/ui/components/SpellContent.kt @@ -0,0 +1,64 @@ +package com.flyinpancake.dndspells.ui.components + +import androidx.compose.foundation.layout.* +import androidx.compose.material.MaterialTheme +import androidx.compose.material.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.text.style.TextOverflow +import androidx.compose.ui.unit.dp +import com.flyinpancake.dndspells.model.Spell + +@Composable +fun SpellContent(spell: Spell) { + val textPadding = Modifier.padding(horizontal = 5.dp) + Column( + Modifier.fillMaxWidth(), + verticalArrangement = Arrangement.Center, + ) { + Row( + Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.SpaceBetween + ) { + Text( + text = spell.name, + modifier = textPadding, + maxLines = 1, + overflow = TextOverflow.Ellipsis, + style = MaterialTheme.typography.h6 + ) + Text( + text = "Level ${spell.level}", + modifier = textPadding, + maxLines = 1, + style = MaterialTheme.typography.h6 + ) + } + Row( + Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.SpaceBetween + ) { + Text( + text = spell.range, + modifier = textPadding, + style = MaterialTheme.typography.body1, + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + Text( + text = spell.time, + modifier = textPadding, + style = MaterialTheme.typography.body1, + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + Text( + text = spell.components, + style = MaterialTheme.typography.body1, + modifier = textPadding, + maxLines = 1, + overflow = TextOverflow.Ellipsis + ) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/ui/components/SpellFilterComponent.kt b/app/src/main/java/com/flyinpancake/dndspells/ui/components/SpellFilterComponent.kt new file mode 100644 index 0000000000000000000000000000000000000000..29b2ac186df24812fc120e029a0999afee8b8fd4 --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/ui/components/SpellFilterComponent.kt @@ -0,0 +1,100 @@ +package com.flyinpancake.dndspells.ui.components + +import androidx.compose.foundation.layout.* +import androidx.compose.material.* +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.unit.dp +import com.flyinpancake.dndspells.ui.logic.SpellFilter +import com.flyinpancake.dndspells.R + +@Composable +fun SpellFilterComponent( + spellFilter: SpellFilter, + onSpellFilterChanged: (SpellFilter) -> Unit, +) { + Column( + Modifier + .fillMaxWidth() + .padding(32.dp), + horizontalAlignment = Alignment.CenterHorizontally + ) { + OutlinedTextField( + value = spellFilter.nameFilter, + onValueChange = { onSpellFilterChanged(spellFilter.copy(nameFilter = it)) }, + label = { + Text(stringResource(R.string.spell_name)) + }, + modifier = Modifier.fillMaxWidth(), + ) + + Divider( + Modifier.padding(vertical = 20.dp) + ) + + Row( + horizontalArrangement = Arrangement.SpaceBetween, + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically + ) { + Row(verticalAlignment = Alignment.CenterVertically) { + Switch( + checked = spellFilter.levelFilterEnabled, + onCheckedChange = { onSpellFilterChanged(spellFilter.copy(levelFilterEnabled = it)) }, + Modifier.padding(end = 20.dp), + ) + Text(stringResource(R.string.filter_spell_level)) + } + + Text("Level " + spellFilter.levelFilter.toInt()) + } + Slider( + value = spellFilter.levelFilter / 9, + onValueChange = { onSpellFilterChanged(spellFilter.copy(levelFilter = it * 9))}, + enabled = spellFilter.levelFilterEnabled + ) + + Divider( + Modifier.padding(vertical = 20.dp) + ) + + Row( + Modifier + .fillMaxWidth() + .padding(vertical = 15.dp), + horizontalArrangement = Arrangement.SpaceBetween, + verticalAlignment = Alignment.CenterVertically + ) { + Switch( + checked = spellFilter.componentFilterEnabled, + onCheckedChange = { onSpellFilterChanged(spellFilter.copy(componentFilterEnabled = it)) }, + Modifier.padding(end = 20.dp) + ) + OutlinedTextField( + value = spellFilter.componentFilter, + onValueChange = { onSpellFilterChanged(spellFilter.copy(componentFilter = it)) }, + label = { Text(stringResource(R.string.filter_components)) }, + enabled = spellFilter.componentFilterEnabled + ) + } + + Divider( + Modifier.padding(vertical = 20.dp) + ) + + Row( + Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Switch( + checked = spellFilter.classFilterEnabled, + onCheckedChange = { onSpellFilterChanged(spellFilter.copy(classFilterEnabled = it)) }) + Text( + text = "Show spells only for own class" + ) + } + } +} diff --git a/app/src/main/java/com/flyinpancake/dndspells/ui/components/SubclassSelector.kt b/app/src/main/java/com/flyinpancake/dndspells/ui/components/SubclassSelector.kt new file mode 100644 index 0000000000000000000000000000000000000000..7618e0173ff6ea551e7c76484a6c99af80275710 --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/ui/components/SubclassSelector.kt @@ -0,0 +1,8 @@ +package com.flyinpancake.dndspells.ui.components + +import androidx.compose.runtime.Composable + +@Composable +fun SubclassSelector(){ + +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/ui/logic/SpellFilter.kt b/app/src/main/java/com/flyinpancake/dndspells/ui/logic/SpellFilter.kt new file mode 100644 index 0000000000000000000000000000000000000000..1708f1fa489d4a09e1e76234bfb7589e2efe2d6f --- /dev/null +++ b/app/src/main/java/com/flyinpancake/dndspells/ui/logic/SpellFilter.kt @@ -0,0 +1,29 @@ +package com.flyinpancake.dndspells.ui.logic + +import com.flyinpancake.dndspells.model.DndCharacter +import com.flyinpancake.dndspells.model.DndClass +import com.flyinpancake.dndspells.model.Spell + +data class SpellFilter ( + val nameFilter: String = "", + val levelFilter: Float = 0f, + val levelFilterEnabled: Boolean = false, + val componentFilter: String = "", + val componentFilterEnabled: Boolean = false, + val classFilter: DndClass, + val classFilterEnabled: Boolean = false, +) { + fun filterSpells(spells: List<Spell>): List<Spell> { + return spells.filter { spell -> + nameFilter.isBlank() || spell.name.contains(nameFilter.trim(), ignoreCase = true) + }.filter { spell -> + !levelFilterEnabled || spell.level == levelFilter.toInt() + }.filter { spell -> + !componentFilterEnabled || componentFilter.all { char -> spell.components.contains(char)} + }.filter { spell -> + !classFilterEnabled || spell.classes.split(",").any { + it.contains(classFilter.legibleName.split(" ")[0]) + } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/flyinpancake/dndspells/viewmodel/CharacterViewModel.kt b/app/src/main/java/com/flyinpancake/dndspells/viewmodel/CharacterViewModel.kt index 009e4c40145b425a19ab28abf57c78109a3278e8..a35dbb744efdc27ea66d76e1fd418053b4fe1fca 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/viewmodel/CharacterViewModel.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/viewmodel/CharacterViewModel.kt @@ -34,4 +34,4 @@ class CharacterViewModel: ViewModel() { fun update(character: DndCharacter) = viewModelScope.launch { repo.update(character) } -} \ No newline at end of file +} diff --git a/app/src/main/java/com/flyinpancake/dndspells/viewmodel/SpellViewModel.kt b/app/src/main/java/com/flyinpancake/dndspells/viewmodel/SpellViewModel.kt index 13182f3d289ebf7c5b4fb8ce03e0a067958703a9..332009e242efa6ee6a2ed2c08bf2d2690863df26 100644 --- a/app/src/main/java/com/flyinpancake/dndspells/viewmodel/SpellViewModel.kt +++ b/app/src/main/java/com/flyinpancake/dndspells/viewmodel/SpellViewModel.kt @@ -30,4 +30,8 @@ class SpellViewModel: ViewModel() { fun nuke() = viewModelScope.launch { repo.nuke() } + + fun get(spellName: String): LiveData<Spell> { + return repo.getSpellByName(spellName) + } } \ No newline at end of file diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_18dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..37a13ed84edbae649c486f3a79ec6d836c5bd3e6 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_18dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_24dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..9ad3e5cf6cbc147ca3607b2819e13d0c99c3be8e Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_24dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_36dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..60d08dbb6964ead8e0b04e20e80b0076ad092b1d Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_36dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_48dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..15b263d6a9da827f6e56862dd3e514ba57a6f07d Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_black_48dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_18dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..520ef271b057fa8c57690b71b4d66d62e3077d45 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_24dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..cbef1c912f88dac2b45f28f988c19e288eb22606 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_36dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..f8acb444883d8c4ee39e2d26f332640f5c0d1f4d Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_48dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..eb87f9035d56ee97a5d0e4f02df9863a3cf1e1dc Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_18dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..f2c024eb2a7b75d42c90d7877939d92d6df77ae2 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_18dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_24dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..1af6cf1af5b21ccc38852a2e890e644b3518353d Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_24dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_36dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..83b6af1cfb4c6f8289ec4219bf35ea566d61d495 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_36dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_48dp.png b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..10c889b99c7ebbf92c45759f0112a777ddae9113 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_dice_5_outline_white_48dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_black_18dp.png b/app/src/main/res/drawable-hdpi/ic_plus_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..79c410e196380cb5d58b1d8bcc015c95aa9af310 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_black_18dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_black_24dp.png b/app/src/main/res/drawable-hdpi/ic_plus_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..f3e4b1d09cbf8caa2e8390a1c54bd895111a823d Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_black_24dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_black_36dp.png b/app/src/main/res/drawable-hdpi/ic_plus_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..2fd546fc71f91922d9e9e3d96203215b64acb685 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_black_36dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_black_48dp.png b/app/src/main/res/drawable-hdpi/ic_plus_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..a027972b1b6ceb2c3d8902476a6a1545cbb67940 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_black_48dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_grey600_18dp.png b/app/src/main/res/drawable-hdpi/ic_plus_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..8443f1e45755f57c7058020331445c9ad3c51f72 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_grey600_24dp.png b/app/src/main/res/drawable-hdpi/ic_plus_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..222a87061ce8a06a1875e0cb26658a74ce7e66ce Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_grey600_36dp.png b/app/src/main/res/drawable-hdpi/ic_plus_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e97e48b0f74eb2bc742bdcc7587ace2581940691 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_grey600_48dp.png b/app/src/main/res/drawable-hdpi/ic_plus_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4e391e38dc6738841ff37559cce352e77f64b9dc Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_white_18dp.png b/app/src/main/res/drawable-hdpi/ic_plus_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..3810a02c45693167cf843b1e72487e731ac222e4 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_white_18dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_white_24dp.png b/app/src/main/res/drawable-hdpi/ic_plus_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..d0526ce66b1960939a0ed283d4a42689253a8714 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_white_24dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_white_36dp.png b/app/src/main/res/drawable-hdpi/ic_plus_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..65d18bd42979510158242b204df745bbc292ae98 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_white_36dp.png differ diff --git a/app/src/main/res/drawable-hdpi/ic_plus_white_48dp.png b/app/src/main/res/drawable-hdpi/ic_plus_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..05025234025a38251a45b800ed5ad293e118c9d9 Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_plus_white_48dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_18dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..6396e98533d41fa58b94cdf2ab7d2466aa18e104 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_18dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_24dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..b18a76c4db21c72ab6dcc30094c05bb49f107e1f Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_24dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_36dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..9ad3e5cf6cbc147ca3607b2819e13d0c99c3be8e Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_36dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_48dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..17ac4e4611345e1d4f4ec653ab56e2ab7c589c0d Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_black_48dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_18dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..31b6452e3ab9eb7582ecf032db4b25e1eb9b41e4 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_24dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..b50a64d15b5480b310a1d4ee610364d97796fb93 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_36dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..cbef1c912f88dac2b45f28f988c19e288eb22606 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_48dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..5d10123ffacb7b88f8b9040aeecb6845960a6f89 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_18dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..1f1d18784d9b753d57e4331b145791bdc7b331bf Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_18dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_24dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..6bd05c46dd698de335bb0b02796343f1a4797614 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_24dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_36dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..1af6cf1af5b21ccc38852a2e890e644b3518353d Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_36dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_48dp.png b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..67ac4cbff302cf607e4615ebdd70ae6eb4ff6f0b Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_dice_5_outline_white_48dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_black_18dp.png b/app/src/main/res/drawable-mdpi/ic_plus_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..02918f5fe0635a979fcafa29c97ffa3d766e7893 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_black_18dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_black_24dp.png b/app/src/main/res/drawable-mdpi/ic_plus_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..c8e9e935ffbdaf3800d1aeb208cb47742e0e345d Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_black_24dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_black_36dp.png b/app/src/main/res/drawable-mdpi/ic_plus_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..f3e4b1d09cbf8caa2e8390a1c54bd895111a823d Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_black_36dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_black_48dp.png b/app/src/main/res/drawable-mdpi/ic_plus_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..514840e66bd21232d6f28aa5a6ed9468fe8ef220 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_black_48dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_grey600_18dp.png b/app/src/main/res/drawable-mdpi/ic_plus_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..802d737d4b7a2d8d31c079e4672aa15181d69611 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_grey600_24dp.png b/app/src/main/res/drawable-mdpi/ic_plus_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..91feaa13ddd2452a76e21ad6b0605ed8d5ab853a Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_grey600_36dp.png b/app/src/main/res/drawable-mdpi/ic_plus_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..222a87061ce8a06a1875e0cb26658a74ce7e66ce Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_grey600_48dp.png b/app/src/main/res/drawable-mdpi/ic_plus_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..7d1896db6d15c1d0f1b7211914f2398ec1001964 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_white_18dp.png b/app/src/main/res/drawable-mdpi/ic_plus_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..3a724b4bcd78d131f7d75b9d14ec8b3760739a10 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_white_18dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_white_24dp.png b/app/src/main/res/drawable-mdpi/ic_plus_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..b3e9ee77773abc7cff10944972c489ae2314e4d2 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_white_24dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_white_36dp.png b/app/src/main/res/drawable-mdpi/ic_plus_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..d0526ce66b1960939a0ed283d4a42689253a8714 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_white_36dp.png differ diff --git a/app/src/main/res/drawable-mdpi/ic_plus_white_48dp.png b/app/src/main/res/drawable-mdpi/ic_plus_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..3eadc0c888b4fc4865a9b1bf5e26c915e3d0e4d8 Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_plus_white_48dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_18dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..9ad3e5cf6cbc147ca3607b2819e13d0c99c3be8e Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_18dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_24dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..17ac4e4611345e1d4f4ec653ab56e2ab7c589c0d Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_24dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_36dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..15b263d6a9da827f6e56862dd3e514ba57a6f07d Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_36dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_48dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..0a6216b56472768ef3b0f0227707621a1889d913 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_black_48dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_18dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..cbef1c912f88dac2b45f28f988c19e288eb22606 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_24dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..5d10123ffacb7b88f8b9040aeecb6845960a6f89 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_36dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..eb87f9035d56ee97a5d0e4f02df9863a3cf1e1dc Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_48dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..0653a4d588dc7820e3425064c3e4d047f276884a Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_18dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..1af6cf1af5b21ccc38852a2e890e644b3518353d Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_18dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_24dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..67ac4cbff302cf607e4615ebdd70ae6eb4ff6f0b Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_24dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_36dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..10c889b99c7ebbf92c45759f0112a777ddae9113 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_36dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_48dp.png b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4c6a7b61c2721614272fa5a728f8b60aa975c098 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_dice_5_outline_white_48dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_black_18dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..f3e4b1d09cbf8caa2e8390a1c54bd895111a823d Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_black_18dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_black_24dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..514840e66bd21232d6f28aa5a6ed9468fe8ef220 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_black_24dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_black_36dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..a027972b1b6ceb2c3d8902476a6a1545cbb67940 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_black_36dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_black_48dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..a39991c3d99f579c5700497721133f5ef114e574 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_black_48dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_grey600_18dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..222a87061ce8a06a1875e0cb26658a74ce7e66ce Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_grey600_24dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..7d1896db6d15c1d0f1b7211914f2398ec1001964 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_grey600_36dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4e391e38dc6738841ff37559cce352e77f64b9dc Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_grey600_48dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e723f8343634b19c4bc14a6b0d7a6840c248944c Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_white_18dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..d0526ce66b1960939a0ed283d4a42689253a8714 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_white_18dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_white_24dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..3eadc0c888b4fc4865a9b1bf5e26c915e3d0e4d8 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_white_24dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_white_36dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..05025234025a38251a45b800ed5ad293e118c9d9 Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_white_36dp.png differ diff --git a/app/src/main/res/drawable-xhdpi/ic_plus_white_48dp.png b/app/src/main/res/drawable-xhdpi/ic_plus_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..d4db8ecf23448ff52e568c44355249d2de719f4c Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_plus_white_48dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_18dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..60d08dbb6964ead8e0b04e20e80b0076ad092b1d Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_18dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_24dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..15b263d6a9da827f6e56862dd3e514ba57a6f07d Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_24dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_36dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..c55bf9a4c468b8a998bcf3cc8e8032246b5634a5 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_36dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4b7831b8745b81e4b8223576af556223803da9a0 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_black_48dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_18dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..f8acb444883d8c4ee39e2d26f332640f5c0d1f4d Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_24dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..eb87f9035d56ee97a5d0e4f02df9863a3cf1e1dc Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_36dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..862e83e0407903c5b77c124fb16430d01f7d805a Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e0e8c18d7cc75021d4d9a367378b79f967a04cb0 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_18dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..83b6af1cfb4c6f8289ec4219bf35ea566d61d495 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_18dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_24dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..10c889b99c7ebbf92c45759f0112a777ddae9113 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_24dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_36dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..dadeaf892f544def35aac4860d1526c75d03ad38 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_36dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e4a19052325ff1c2d375e9bde3cd30aef28226e2 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_dice_5_outline_white_48dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_black_18dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..2fd546fc71f91922d9e9e3d96203215b64acb685 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_black_18dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_black_24dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..a027972b1b6ceb2c3d8902476a6a1545cbb67940 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_black_24dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_black_36dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..6344724836028776d6cb8e3a4cea701f53bf0a79 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_black_36dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_black_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..8187b4d1221936b976956df25b7cc89e37358a54 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_black_48dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_18dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e97e48b0f74eb2bc742bdcc7587ace2581940691 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_24dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4e391e38dc6738841ff37559cce352e77f64b9dc Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_36dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..193dc2e9747d1e5dfe554129683e471ca6d29fd3 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e993a737774a3ad1724d366bb85875d255914499 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_white_18dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..65d18bd42979510158242b204df745bbc292ae98 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_white_18dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_white_24dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..05025234025a38251a45b800ed5ad293e118c9d9 Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_white_24dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_white_36dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4bac3f0dc301330e9e715ad5ac6c7cb9ab0c3b8b Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_white_36dp.png differ diff --git a/app/src/main/res/drawable-xxhdpi/ic_plus_white_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_plus_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..b9d19a15a7b628f1cd4034e8f477629de32db5ca Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_plus_white_48dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_18dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..15b263d6a9da827f6e56862dd3e514ba57a6f07d Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_18dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_24dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..0a6216b56472768ef3b0f0227707621a1889d913 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_24dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_36dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4b7831b8745b81e4b8223576af556223803da9a0 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_36dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..fd7f49a21d873300b15b906008533bf2c931a697 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_black_48dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_18dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..eb87f9035d56ee97a5d0e4f02df9863a3cf1e1dc Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_24dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..0653a4d588dc7820e3425064c3e4d047f276884a Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_36dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e0e8c18d7cc75021d4d9a367378b79f967a04cb0 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..74b95fd60a27d81c852a65b72b9d4410c45941c8 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_18dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..10c889b99c7ebbf92c45759f0112a777ddae9113 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_18dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_24dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4c6a7b61c2721614272fa5a728f8b60aa975c098 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_24dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_36dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e4a19052325ff1c2d375e9bde3cd30aef28226e2 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_36dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..010284f895ff271fd5d1543027bccc7decf54048 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_dice_5_outline_white_48dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_black_18dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..a027972b1b6ceb2c3d8902476a6a1545cbb67940 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_18dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_black_24dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..a39991c3d99f579c5700497721133f5ef114e574 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_24dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_black_36dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..71ee250ff0ccfb1a0a2c4c4bfaafc75efd6449ee Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_36dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_black_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..684fcfc01a325077ebb759becbab6bd897e0e123 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_black_48dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_18dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4e391e38dc6738841ff37559cce352e77f64b9dc Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_18dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_24dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e723f8343634b19c4bc14a6b0d7a6840c248944c Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_24dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_36dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..2c023f8c802f65f4637b81bed90488a68b68dd26 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_36dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..728998eb0394ae234e43c633f0dbf651f46dd593 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_grey600_48dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_white_18dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_18dp.png new file mode 100644 index 0000000000000000000000000000000000000000..05025234025a38251a45b800ed5ad293e118c9d9 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_18dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_white_24dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_24dp.png new file mode 100644 index 0000000000000000000000000000000000000000..b336422c271970456f2b6f09d65ebadfdc2fffae Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_24dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_white_36dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_36dp.png new file mode 100644 index 0000000000000000000000000000000000000000..0326d233396df678291041e2e598bed8b851d0e2 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_36dp.png differ diff --git a/app/src/main/res/drawable-xxxhdpi/ic_plus_white_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..0495b97f867045cd5fdca680a6df7e94de00c4a0 Binary files /dev/null and b/app/src/main/res/drawable-xxxhdpi/ic_plus_white_48dp.png differ diff --git a/app/src/main/res/drawable/dice_5_outline.xml b/app/src/main/res/drawable/dice_5_outline.xml new file mode 100644 index 0000000000000000000000000000000000000000..a8bbbd90aff92f41ef2be2abfac8f4223758c663 --- /dev/null +++ b/app/src/main/res/drawable/dice_5_outline.xml @@ -0,0 +1,8 @@ +<!-- drawable/dice-5-outline.xml --> +<vector xmlns:android="http://schemas.android.com/apk/res/android" + android:height="24dp" + android:width="24dp" + android:viewportWidth="24" + android:viewportHeight="24"> + <path android:fillColor="#000" android:pathData="M19 5V19H5V5H19M19 3H5C3.9 3 3 3.9 3 5V19C3 20.1 3.9 21 5 21H19C20.1 21 21 20.1 21 19V5C21 3.9 20.1 3 19 3M7.5 6C6.7 6 6 6.7 6 7.5S6.7 9 7.5 9 9 8.3 9 7.5 8.3 6 7.5 6M16.5 15C15.7 15 15 15.7 15 16.5C15 17.3 15.7 18 16.5 18C17.3 18 18 17.3 18 16.5C18 15.7 17.3 15 16.5 15M16.5 6C15.7 6 15 6.7 15 7.5S15.7 9 16.5 9C17.3 9 18 8.3 18 7.5S17.3 6 16.5 6M12 10.5C11.2 10.5 10.5 11.2 10.5 12S11.2 13.5 12 13.5 13.5 12.8 13.5 12 12.8 10.5 12 10.5M7.5 15C6.7 15 6 15.7 6 16.5C6 17.3 6.7 18 7.5 18S9 17.3 9 16.5C9 15.7 8.3 15 7.5 15Z" /> +</vector> \ No newline at end of file diff --git a/app/src/main/res/drawable/plus.xml b/app/src/main/res/drawable/plus.xml new file mode 100644 index 0000000000000000000000000000000000000000..fe500883a43e8551442e7c9282d6a2538de1f13f --- /dev/null +++ b/app/src/main/res/drawable/plus.xml @@ -0,0 +1,8 @@ +<!-- drawable/plus.xml --> +<vector xmlns:android="http://schemas.android.com/apk/res/android" + android:height="24dp" + android:width="24dp" + android:viewportWidth="24" + android:viewportHeight="24"> + <path android:fillColor="#000" android:pathData="M19,13H13V19H11V13H5V11H11V5H13V11H19V13Z" /> +</vector> \ No newline at end of file diff --git a/app/src/main/res/layout/activity_main.xml b/app/src/main/res/layout/activity_main.xml index 367b4f3779cb75b882922249f116c6b53d9936cc..62456f373621490da5a2005475dbaa42831852fd 100644 --- a/app/src/main/res/layout/activity_main.xml +++ b/app/src/main/res/layout/activity_main.xml @@ -4,6 +4,7 @@ <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" + android:id="@+id/fabAddCharacter" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".MainActivity"> @@ -18,31 +19,21 @@ android:id="@+id/toolbar" android:layout_width="match_parent" android:layout_height="wrap_content" - app:popupTheme="@style/Theme.DndSpells.PopupOverlay"/> + app:title="@string/select_your_character" + app:popupTheme="@style/Theme.DndSpells.PopupOverlay" /> </com.google.android.material.appbar.AppBarLayout> - <TextView - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:text="@string/select_your_character" - android:textSize="32sp" - app:layout_constraintBottom_toTopOf="@+id/rvCharacterList" - app:layout_constraintLeft_toLeftOf="parent" - app:layout_constraintRight_toRightOf="parent" - app:layout_constraintTop_toTopOf="parent" /> - <androidx.recyclerview.widget.RecyclerView android:id="@+id/rvCharacterList" android:layout_width="match_parent" android:layout_height="0dp" - android:layout_marginTop="150dp" + app:layoutManager="LinearLayoutManager" app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="parent" - app:layout_constraintTop_toTopOf="parent" - app:layoutManager="LinearLayoutManager"> + app:layout_constraintTop_toBottomOf="@+id/main_appbar"> </androidx.recyclerview.widget.RecyclerView> diff --git a/app/src/main/res/layout/activity_profile.xml b/app/src/main/res/layout/activity_profile.xml deleted file mode 100644 index aedecc2e041970bb0cb195f8a451a724d820cc26..0000000000000000000000000000000000000000 --- a/app/src/main/res/layout/activity_profile.xml +++ /dev/null @@ -1,45 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:app="http://schemas.android.com/apk/res-auto" - xmlns:tools="http://schemas.android.com/tools" - android:layout_width="match_parent" - android:layout_height="match_parent" - tools:context=".ProfileActivity"> - - <TextView - android:id="@+id/tvCharacterName" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - tools:text="Klattic" - android:textAppearance="@style/TextAppearance.AppCompat.Display1" - android:transitionName="character_name" - app:layout_constraintBottom_toBottomOf="@+id/imCharacterArt" - app:layout_constraintEnd_toStartOf="@+id/imCharacterArt" - app:layout_constraintHorizontal_bias="0.465" - app:layout_constraintStart_toStartOf="parent" - app:layout_constraintTop_toTopOf="@+id/imCharacterArt" /> - - <ImageView - android:id="@+id/imCharacterArt" - android:transitionName="character_art" - - android:layout_width="106dp" - android:layout_height="104dp" - android:layout_marginTop="24dp" - android:layout_marginEnd="24dp" - app:layout_constraintEnd_toEndOf="parent" - app:layout_constraintTop_toTopOf="parent" - tools:srcCompat="@drawable/dnd_logo" /> - - <androidx.recyclerview.widget.RecyclerView - android:id="@+id/rvSpellList" - android:layout_width="409dp" - android:layout_height="601dp" - android:layout_marginStart="16dp" - android:layout_marginTop="24dp" - android:layout_marginEnd="16dp" - app:layout_constraintBottom_toBottomOf="parent" - app:layout_constraintEnd_toEndOf="parent" - app:layout_constraintStart_toStartOf="parent" - app:layout_constraintTop_toBottomOf="@+id/imCharacterArt" /> -</androidx.constraintlayout.widget.ConstraintLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/recyclerview_main_menu_row.xml b/app/src/main/res/layout/recyclerview_main_menu_row.xml index efa6c1bb1214ccfd98a36488a4a3884f4eec8ff3..14880c6dc364f37284c164e2abb61fbd1bf1877c 100644 --- a/app/src/main/res/layout/recyclerview_main_menu_row.xml +++ b/app/src/main/res/layout/recyclerview_main_menu_row.xml @@ -26,22 +26,8 @@ android:layout_height="wrap_content" android:layout_marginStart="32dp" app:layout_constraintBottom_toBottomOf="parent" - app:layout_constraintEnd_toStartOf="@+id/imCharacterArt" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@+id/tvCharacterName" tools:text="level 6 paladin" /> - <ImageView - android:id="@+id/imCharacterArt" - android:layout_width="150dp" - android:layout_height="0dp" - android:layout_marginEnd="16dp" - android:transitionName="character_art" - app:layout_constraintBottom_toBottomOf="parent" - app:layout_constraintEnd_toEndOf="parent" - app:layout_constraintTop_toTopOf="parent" - - android:contentDescription="@string/character_avatar_of" - tools:srcCompat="@drawable/dnd_logo" /> - </androidx.constraintlayout.widget.ConstraintLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/recyclerview_spell_row.xml b/app/src/main/res/layout/recyclerview_spell_row.xml deleted file mode 100644 index 63b2a8d6af31675c4ce371c91785565f43ee5431..0000000000000000000000000000000000000000 --- a/app/src/main/res/layout/recyclerview_spell_row.xml +++ /dev/null @@ -1,62 +0,0 @@ -<?xml version="1.0" encoding="UTF-8" ?> -<androidx.constraintlayout.widget.ConstraintLayout xmlns:app="http://schemas.android.com/apk/res-auto" - xmlns:tools="http://schemas.android.com/tools" - xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="match_parent" - android:layout_height="wrap_content"> - - <TextView - android:id="@+id/tvSpellName" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:layout_marginStart="32dp" - android:layout_marginTop="16dp" - android:textSize="28sp" - app:layout_constraintStart_toStartOf="parent" - app:layout_constraintTop_toTopOf="parent" - tools:text="Power word kill" /> - - <TextView - android:id="@+id/SpellLevel" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:layout_marginEnd="32dp" - android:textSize="28sp" - app:layout_constraintEnd_toEndOf="parent" - app:layout_constraintTop_toTopOf="@+id/tvSpellName" - tools:text="Level 9" /> - - - <TextView - android:id="@+id/SpellSchool" - android:layout_width="wrap_content" - android:layout_height="27dp" - android:layout_marginStart="32dp" - android:layout_marginTop="8dp" - android:layout_marginBottom="8dp" - android:textSize="20sp" - app:layout_constraintBottom_toBottomOf="parent" - app:layout_constraintStart_toStartOf="parent" - app:layout_constraintTop_toBottomOf="@+id/tvSpellName" - app:layout_constraintVertical_bias="1.0" - tools:text="school" /> - - <TextView - android:id="@+id/SpellComponents" - android:layout_width="0dp" - android:layout_height="19dp" - android:layout_marginStart="16dp" - android:layout_marginEnd="32dp" - android:layout_marginBottom="16dp" - android:ellipsize="end" - android:maxLines="1" - app:layout_constraintBottom_toBottomOf="parent" - app:layout_constraintEnd_toEndOf="parent" - app:layout_constraintStart_toEndOf="@id/SpellSchool" - app:layout_constraintTop_toBottomOf="@+id/SpellLevel" - app:layout_constraintVertical_bias="1.0" - tools:text="ComponentsComponentsComponentsComponentsComponents" /> - - - -</androidx.constraintlayout.widget.ConstraintLayout> \ No newline at end of file diff --git a/app/src/main/res/readme.txt b/app/src/main/res/readme.txt new file mode 100644 index 0000000000000000000000000000000000000000..f8a80f65331f4c868cc8b09626137168ecb06490 --- /dev/null +++ b/app/src/main/res/readme.txt @@ -0,0 +1,5 @@ +Thanks for visiting MaterialDesignIcons.com +Check back often for new icons and follow @MaterialIcons for updates. + +Icon: dice-5-outline +By: Michael Irigoyen \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index cedd03aad4eb3bf3ee03b28d4ab0f27808c6660c..ef08bb79d779b3b63558f628b96f91ce854abe84 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -17,7 +17,11 @@ <string name="add_new_character">Add New Character</string> <string name="title_activity_character_details">CharacterDetailsActivity</string> <string name="title_activity_select_spells">SelectSpellsActivity</string> - <string name="select_spells">\" - select spells\"</string> + <string name="select_spells">- select spells</string> <string name="title_activity_ruinable">RuinableActivity</string> <string name="modify_character">Modify Character</string> + <string name="filter_components">Filter Components</string> + <string name="filter_spell_level">Filter Spell Level</string> + <string name="spell_name">Spell Name</string> + <string name="you_rolled">You rolled:</string> </resources> \ No newline at end of file diff --git a/build.gradle b/build.gradle index 910dc1b231d7db66fda085ab792ef47c7a73cd00..3af8e665a749899c24b8a67c0535d89e2be373c4 100644 --- a/build.gradle +++ b/build.gradle @@ -2,7 +2,8 @@ buildscript { ext { kotlin_version = '1.6.0' - compose_version = '1.1.0-beta04' + compose_version = '1.1.0-rc01' + agp_version = '7.0.4' } repositories { @@ -11,7 +12,8 @@ buildscript { } dependencies { - classpath 'com.android.tools.build:gradle:7.0.4' + classpath "com.android.tools.build:gradle:$agp_version" + classpath "com.google.gms:google-services:4.3.10" classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version" classpath "org.jetbrains.kotlin:kotlin-serialization:$kotlin_version" diff --git a/changes.md b/changes.md new file mode 100644 index 0000000000000000000000000000000000000000..cb1fdf2f7b83e798f3c7bee224f08c8e2ca3d512 --- /dev/null +++ b/changes.md @@ -0,0 +1,9 @@ +- ne json serialize +- szürcs + - level + - név +- slotok +- roll +- character edit +- doksi (szkrínsot, meg ilyenek, funkciók használata) +- permission helyes kezelése \ No newline at end of file diff --git a/doc/Screenshots/Screenshot_20211217_140502.png b/doc/Screenshots/Screenshot_20211217_140502.png new file mode 100644 index 0000000000000000000000000000000000000000..f7d91824ab1432b871c9e222d1de146cc42c911a Binary files /dev/null and b/doc/Screenshots/Screenshot_20211217_140502.png differ diff --git a/doc/Screenshots/Screenshot_20211217_142305.png b/doc/Screenshots/Screenshot_20211217_142305.png new file mode 100644 index 0000000000000000000000000000000000000000..4465b5acdb392c76f3ff7554f398455eb6a70ae2 Binary files /dev/null and b/doc/Screenshots/Screenshot_20211217_142305.png differ diff --git a/doc/Screenshots/Screenshot_20211217_145142.png b/doc/Screenshots/Screenshot_20211217_145142.png new file mode 100644 index 0000000000000000000000000000000000000000..37cac1ba9585cabc8237616233373118fd4f8fc6 Binary files /dev/null and b/doc/Screenshots/Screenshot_20211217_145142.png differ diff --git a/doc/Screenshots/characterscreen.jpg b/doc/Screenshots/characterscreen.jpg new file mode 100644 index 0000000000000000000000000000000000000000..b3890f6a24855cfb7b5729737ef9f27f2f0e9acd Binary files /dev/null and b/doc/Screenshots/characterscreen.jpg differ diff --git a/doc/Screenshots/selectscreen.jpg b/doc/Screenshots/selectscreen.jpg new file mode 100644 index 0000000000000000000000000000000000000000..8f119e94399d4f35be65615f12a7c619a1a3a89b Binary files /dev/null and b/doc/Screenshots/selectscreen.jpg differ diff --git a/doc/Screenshots/spellscreen.jpg b/doc/Screenshots/spellscreen.jpg new file mode 100644 index 0000000000000000000000000000000000000000..a3164f51cf651fc8e5817beb58e686605af35bd7 Binary files /dev/null and b/doc/Screenshots/spellscreen.jpg differ diff --git a/doc/android-doc.org b/doc/android-doc.org new file mode 100644 index 0000000000000000000000000000000000000000..973b1e2e30ed4fcd9a68c7ef87175426189758e0 --- /dev/null +++ b/doc/android-doc.org @@ -0,0 +1,87 @@ +#+TITLE: D&D Spellbook Alkalmazás Dokimentáció +#+author: Pálvölgyi Domonkos (FBYGH3) +#+date: 2021-12-17 +#+LATEX_HEADER: \usepackage{placeins} + +* Röviden az alkalmazásról + +A play storeon van már néhány alkalmazás ami a Dungeons & Dragaons játékosok életét könnyebbíti meg, viszont ezek nagy része a funkciók java részét előfizetés mögé zárja. + +Az én alkalmazásom nagyon egyszerű, átlátható és nem utolsó sorban natív teljesítménnyel fog bírni. + +Az alkalmazást olyanoknak szánom, akik: + 1. Nem szeretnek előfizetéses modellben gondolkodni. + 2. Kis méretű és komplexitású programot szeretnének használni. + 3. Preferálják a FOSS alkalmazásokat. + +* Specifikáció +1. Az alkalmazásban karaktereket táolunk és hozzájuk kapcsolódó spelleket, illetve egy nagy listát az összes elérhető. +2. A spellek importálhatóak XML formátumból (kompatibilis a FightClub alkalmazás formátumával). +3. Karakterekhez spelleket tudunk renelni. +4. Ha a spellhez tartozik kockadobás, azt el tudjuk végezni. +5. Amikor egy karakterhez hozzárendelünk spelleket, tudunk keresni és osztály illetve komponensek alapján szűrni is. +6. Az alkalmazás támogatja az Android Light/Dark témáját. + +* Bemutatás +** Főképernyő +*** Karakterek listája +#+caption: Főképernyő +#+ATTR_LATEX: :height 0.4\textwidth +[[./Screenshots/Screenshot_20211217_140502.png]] + +A főképernyőn a karakterek vannak kilistázva, akiket a felhasználó felvett. +Ha a karakterre kattintunk, megnyitja a details nézetét, ami hozzá tartozik, és ahol a spelleket lehet nézni. +Ha a kakakteren hosszan kattintunk, akkor a karaktermódosító képernyő jelenik meg. +\FloatBarrier +*** Menü +#+caption: Főképernyőn lévő menü +#+ATTR_LATEX: :height 0.4\textwidth +[[./Screenshots/Screenshot_20211217_142305.png]] + +\FloatBarrier +A főképernyőn lévő menübpl lehet új karaktert létrehozni és a spellek listáját importálni. +** Karakter hozzáadása, módisítása +#+caption: Karakterkészítési képernyő +#+ATTR_LATEX: :height 0.4\textwidth +[[./Screenshots/Screenshot_20211217_145142.png]] + +\FloatBarrier +A karakter hozzáadás képernyőn hozzáadhatunk az adatbázishoz egy új karaktert, névvel, classzal és szinttel. + +A FloatingActionButton megnyomásakor az alkalmazás ellenőrzi hogy érvényes-e a karakter. +Ha a karakter nem érvényes, akkor egy üzenetben jelzi ezt a felhasználónak. + +Ha módosításként nyitottuk meg a képernyőt akkor amelyik értéket megváltoztatjuk, csak az fog megváltozni a kakakteren. +** Karakterképernyő +#+caption: Karakterképernyő +#+ATTR_LATEX: :height 0.4\textwidth +[[./Screenshots/characterscreen.jpg]] + +\FloatBarrier +A karakterképernyőn láthatjuk a karakterhez tartozó spelleket. +A bal oldalon a karakterhez még nem vettünk fel semmit, a jobb oldalon viszont már felvettüjk 2 db hármas szintű varázslatot. + +Az egyik spell neve mellett van egy dobókocka. Ez azt jelenti, hogy a spellhez tartozik kockadobás is. +A kocka ikonra kattintva kidobhatjuk ennek az értékét. + +** Spell képernyő +#+caption: 2 különböző spell képernyő +#+attr_latex: :height 0.4\textwidth +[[./Screenshots/spellscreen.jpg]] + +\FloatBarrier +Az előbbi 2 spell részletező képernyőji. +Hasonló elven, mivel a Call Lightning spell tartalmaz kockadobást, itt is el tudjuk dobni a kockát, aminek az eredménye ugyan olyan snackbarban jelenik meg. +** Spell kereső képernyő + +#+caption: Spellkereső +#+attr_latex: :height 0.4\textwidth +[[./Screenshots/selectscreen.jpg]] + +\FloatBarrier +Az add spells képernyőn keresketünk és szűrhetünk spelleket, majd hozzá is adhatjuk a karakterünkhöz. + +A kereső tud: +- keresni a spell nevére +- szűrni a spell szintjére +- szűrni a spell komponenseire diff --git a/doc/android-doc.pdf b/doc/android-doc.pdf new file mode 100644 index 0000000000000000000000000000000000000000..95c7296293bd4ee45ea70513f81ef5a5606cfc5d Binary files /dev/null and b/doc/android-doc.pdf differ diff --git a/doc/android-doc.tex b/doc/android-doc.tex new file mode 100644 index 0000000000000000000000000000000000000000..7c4bf2928e0b61024c5121732e516965dba746d8 --- /dev/null +++ b/doc/android-doc.tex @@ -0,0 +1,142 @@ +% Created 2021-12-17 Fri 15:34 +% Intended LaTeX compiler: pdflatex +\documentclass[11pt]{article} +\usepackage[utf8]{inputenc} +\usepackage[T1]{fontenc} +\usepackage{graphicx} +\usepackage{longtable} +\usepackage{wrapfig} +\usepackage{rotating} +\usepackage[normalem]{ulem} +\usepackage{amsmath} +\usepackage{amssymb} +\usepackage{capt-of} +\usepackage{hyperref} +\usepackage{placeins} +\author{Pálvölgyi Domonkos (FBYGH3)} +\date{2021-12-17} +\title{D\&D Spellbook Alkalmazás Dokimentáció} +\hypersetup{ + pdfauthor={Pálvölgyi Domonkos (FBYGH3)}, + pdftitle={D\&D Spellbook Alkalmazás Dokimentáció}, + pdfkeywords={}, + pdfsubject={}, + pdfcreator={Emacs 27.2 (Org mode 9.6)}, + pdflang={English}} +\begin{document} + +\maketitle +\tableofcontents + + +\section{Röviden az alkalmazásról} +\label{sec:org8561d27} + +A play storeon van már néhány alkalmazás ami a Dungeons \& Dragaons játékosok életét könnyebbíti meg, viszont ezek nagy része a funkciók java részét előfizetés mögé zárja. + +Az én alkalmazásom nagyon egyszerű, átlátható és nem utolsó sorban natív teljesítménnyel fog bírni. + +Az alkalmazást olyanoknak szánom, akik: +\begin{enumerate} +\item Nem szeretnek előfizetéses modellben gondolkodni. +\item Kis méretű és komplexitású programot szeretnének használni. +\item Preferálják a FOSS alkalmazásokat. +\end{enumerate} + +\section{Specifikáció} +\label{sec:orgfb557ae} +\begin{enumerate} +\item Az alkalmazásban karaktereket táolunk és hozzájuk kapcsolódó spelleket, illetve egy nagy listát az összes elérhető. +\item A spellek importálhatóak XML formátumból (kompatibilis a FightClub alkalmazás formátumával). +\item Karakterekhez spelleket tudunk renelni. +\item Ha a spellhez tartozik kockadobás, azt el tudjuk végezni. +\item Amikor egy karakterhez hozzárendelünk spelleket, tudunk keresni és osztály illetve komponensek alapján szűrni is. +\item Az alkalmazás támogatja az Android Light/Dark témáját. +\end{enumerate} + +\section{Bemutatás} +\label{sec:org1c4121f} +\subsection{Főképernyő} +\label{sec:orgf51912f} +\subsubsection{Karakterek listája} +\label{sec:org7688390} +\begin{figure}[htbp] +\centering +\includegraphics[height=0.4\textwidth]{./Screenshots/Screenshot_20211217_140502.png} +\caption{Főképernyő} +\end{figure} + +A főképernyőn a karakterek vannak kilistázva, akiket a felhasználó felvett. +Ha a karakterre kattintunk, megnyitja a details nézetét, ami hozzá tartozik, és ahol a spelleket lehet nézni. +Ha a kakakteren hosszan kattintunk, akkor a karaktermódosító képernyő jelenik meg. +\FloatBarrier +\subsubsection{Menü} +\label{sec:orgdbc40de} +\begin{figure}[htbp] +\centering +\includegraphics[height=0.4\textwidth]{./Screenshots/Screenshot_20211217_142305.png} +\caption{Főképernyőn lévő menü} +\end{figure} + +\FloatBarrier +A főképernyőn lévő menübpl lehet új karaktert létrehozni és a spellek listáját importálni. +\subsection{Karakter hozzáadása, módisítása} +\label{sec:org71d9680} +\begin{figure}[htbp] +\centering +\includegraphics[height=0.4\textwidth]{./Screenshots/Screenshot_20211217_145142.png} +\caption{Karakterkészítési képernyő} +\end{figure} + +\FloatBarrier +A karakter hozzáadás képernyőn hozzáadhatunk az adatbázishoz egy új karaktert, névvel, classzal és szinttel. + +A FloatingActionButton megnyomásakor az alkalmazás ellenőrzi hogy érvényes-e a karakter. +Ha a karakter nem érvényes, akkor egy üzenetben jelzi ezt a felhasználónak. + +Ha módosításként nyitottuk meg a képernyőt akkor amelyik értéket megváltoztatjuk, csak az fog megváltozni a kakakteren. +\subsection{Karakterképernyő} +\label{sec:org55447fb} +\begin{figure}[htbp] +\centering +\includegraphics[height=0.4\textwidth]{./Screenshots/characterscreen.jpg} +\caption{Karakterképernyő} +\end{figure} + +\FloatBarrier +A karakterképernyőn láthatjuk a karakterhez tartozó spelleket. +A bal oldalon a karakterhez még nem vettünk fel semmit, a jobb oldalon viszont már felvettüjk 2 db hármas szintű varázslatot. + +Az egyik spell neve mellett van egy dobókocka. Ez azt jelenti, hogy a spellhez tartozik kockadobás is. +A kocka ikonra kattintva kidobhatjuk ennek az értékét. + +\subsection{Spell képernyő} +\label{sec:orgc7255f2} +\begin{figure}[htbp] +\centering +\includegraphics[height=0.4\textwidth]{./Screenshots/spellscreen.jpg} +\caption{2 különböző spell képernyő} +\end{figure} + +\FloatBarrier +Az előbbi 2 spell részletező képernyőji. +Hasonló elven, mivel a Call Lightning spell tartalmaz kockadobást, itt is el tudjuk dobni a kockát, aminek az eredménye ugyan olyan snackbarban jelenik meg. +\subsection{Spell kereső képernyő} +\label{sec:org3ed6803} + +\begin{figure}[htbp] +\centering +\includegraphics[height=0.4\textwidth]{./Screenshots/selectscreen.jpg} +\caption{Spellkereső} +\end{figure} + +\FloatBarrier +Az add spells képernyőn keresketünk és szűrhetünk spelleket, majd hozzá is adhatjuk a karakterünkhöz. + +A kereső tud: +\begin{itemize} +\item keresni a spell nevére +\item szűrni a spell szintjére +\item szűrni a spell komponenseire +\end{itemize} +\end{document} diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 10f8d6bf3c743680ef41ef0ea73774722edcb1be..fa44eebf7e962f01625aa762de71cdc4175015f9 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ -#Sun Nov 07 11:54:24 CET 2021 +#Sun Dec 19 23:09:51 CET 2021 distributionBase=GRADLE_USER_HOME -distributionUrl=https\://services.gradle.org/distributions/gradle-7.0.2-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.2-bin.zip distributionPath=wrapper/dists zipStorePath=wrapper/dists zipStoreBase=GRADLE_USER_HOME