Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions Building.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@

## Using CLI and Gradle

Follow theese steps if you don't have installed IntelliJ/Andoid Studio and want to build `Smupe!` using Gradle CLI.
Follow these steps if you don't have installed IntelliJ/Android Studio and want to build `Smupe!` using Gradle CLI.

1. Verify installation of JDK before you begin:

Expand Down Expand Up @@ -44,11 +44,11 @@ Follow theese steps if you don't have installed IntelliJ/Andoid Studio and want

## Using Android Studio or IntelliJ IDEA

If you prefer to use IDE to build, follow theese steps:
If you prefer to use IDE to build, follow these steps:

1. Open IDE and clone project by clicking `Get from VCS`
2. Select `Repository URL` -> `Git` and enter the repo URL
3. Click `Clone` and wait when project load
4. Android plugin will show an Android SDK selector pop-up message, where you should select installed Andoid SDK. If there's nothing, follow instructions to install correct SDK.
4. Android plugin will show an Android SDK selector pop-up message, where you should select installed Android SDK. If there's nothing, follow instructions to install correct SDK.
5. After that, click on `Build` > `Build APKs`
6. If build succeeds, click to `locate` in notification. The APK will be available in `debug` directory
17 changes: 9 additions & 8 deletions Contributing.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ I was added experimental ACRA support to the project, but now it is disabled. So
* device model and OS version
* logcat output for `net.blusutils.smupe.foss` (search in the Internet how to collect it)
* screen recording
* additional context (e. g. Internet connection, app permissions or anything you think is relevant)
* additional context (e.g. Internet connection, app permissions or anything you think is relevant)

## Proposing Enhancements

Expand All @@ -26,21 +26,22 @@ Describe your idea in details, as clear as possible. If you can, attach screensh

## Pull Requests (changes in code)

If you want to contribute code to the project, remember:
If you want to contribute code to the project, please:

* split your PRs to small ones (if possible)
* if you decided to change the UI, please attach screenshots or mockups
* if you decided to change the UI, attach screenshots or mockups
* if you decided to change app architecture, create a *draft* PR, and, until we confirm the changes, don't turn it to normal PR
* if you want to add a new translation, also create a draft PR
* PRs with very small changes will be rejected (create issue instead)
* small changes is: a typo fix, a comment change, a small UI change (like padding intervals), etc.
* in issue just copy link to line(s) that should be changed in the code and add changes codeblock
* PRs with very small changes will be rejected (create an issue instead)
* small changes is: a typo fix, a small comment change or addition, a small UI change (like padding intervals), etc.
* when create issue just copy permalink to line(s) that should be changed in the code and add changes to fenced (\```) codeblock
* PRs that add or change code comments is allowed, but only if it useful enough
* adding new dependencies is disallowed, unless it is absolutely necessary (we will try to decide it in conversation)
* **don't propose breaking changes in PRs!!!** I mean
* **don't propose breaking changes in PRs!!!**
* I mean:
* breaking API changes (so app update cannot be installed above the current version)
* global and big UI changes (it will confuse users)
* anything that may be harmful for the user experience (including ADS, spyware, etc.)
* anything that may be harmful for the user experience (including advertisements, spyware, etc.)
* ProtoBufs messages and Room DB entities changes without defined migrations
* never use destructive migrations
* for ProtoBufs please use reserved fields if it really necessary
Expand Down
16 changes: 8 additions & 8 deletions Readme.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# Smupe!

> [!WARNING]
> **Smupe!** currently in early early alpha stage. Report any bugs to issues and contribute!
> **Smupe!** currently in early, really early alpha stage. Report any bugs to issues and contribute!

"Show me 'ur pictures, eternally!"

Expand All @@ -13,9 +13,9 @@ Choose from a variety of image sources, from art & landscapes to memes & animals

**Smupe!** is easy to use. Just swipe to get a new image!

Found something interesting? Tap ~~twice~~ on heart to save it to Favourites!
Found something interesting? Tap twice or on heart to save it to Favourites!

Want to share or view original? ~~Swipe right~~ tap on action button to show context buttons!
Want to share or view original? Tap on action button to show context buttons!

Get bored with such stream of images? Switch to another one, the API-DEFs tab contain some built-in, and you can add your own.

Expand Down Expand Up @@ -61,19 +61,19 @@ You can download release APK from [GitHub releases](https://github.com/EgorBron/
There is no release in any app stores yet, but soon,
I will prepare for publishing in Play Market and F-Droid.

#### Will there be versions for Watch OS/Android TV/desktop platforms/iOS/Web?
#### Will there be versions for WearOS/Android TV/desktop platforms/iOS/Web?

Support for Watch OS & Android TV is planned, but not in the near future.

Web version is also will be done. Stay tuned for updates!

Desktop and iOS versions will require migration to the Compose Multiplatform (or the more radical way - Flutter).
To do so, I need to rewirite some parts of app logic entirely.
To do so, I need to rewrite some parts of app logic entirely.
That's really time-consuming, so I'm not going to do it soon.

#### Can I use \<insert-any-image-source-here>?

Proably! As long as it matches all requirements of API-DEF specs. You'll need to write a new API-DEF (i.e. request schema processor) for it.
Probably! As long as it matches all requirements of API-DEF specs. You'll need to write a new API-DEF (i.e. request schema processor) for it.

If you about the copyright... Use at your own risk. I have no warranty or liability for any claim, damage or any other kind, because app is just an interface to interact with such. It's not mine or app's job to check, the images are safe to retrieve or use, or not.

Expand Down Expand Up @@ -124,11 +124,11 @@ So, finally, I decided:

#### The code is bad 😬! No best practices used!

Calm down! That's my first expirience in Compose!
Calm down! That's my first experience in Compose!

Instead of throwing rotten tomatoes at me, better help improve the app!

> For example, I want to get rid of side effects and buisness logic in composables, properly share data between them, use coroutines much more, etc.
> For example, I want to get rid of side effects and business logic in @Composables, properly share data between them, use coroutines much more, etc.

See [Contributing](./Contributing.md) to know how you can help!

Expand Down
23 changes: 11 additions & 12 deletions app/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -37,8 +37,8 @@ android {
isDebuggable = true
}
release {
isMinifyEnabled = true
isShrinkResources = true
// isMinifyEnabled = true
// isShrinkResources = true
proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
signingConfig = signingConfigs.getByName("debug")
}
Expand Down Expand Up @@ -95,21 +95,20 @@ tasks.withType<DokkaTask>().configureEach {

dependencies {

implementation(platform("androidx.compose:compose-bom:2023.08.00"))
androidTestImplementation(platform("androidx.compose:compose-bom:2023.08.00"))
implementation(platform("androidx.compose:compose-bom:2024.02.00"))
implementation(project(":common"))
androidTestImplementation(platform("androidx.compose:compose-bom:2024.02.00"))
// Documentation
dokkaPlugin("org.jetbrains.dokka:android-documentation-plugin:1.9.10")

// AndroidX (Jetpack) dependencies
implementation("androidx.core:core-ktx:1.12.0")
implementation("androidx.core:core-ktx:1.13.0")
implementation("androidx.lifecycle:lifecycle-runtime-ktx:2.7.0")
implementation("androidx.activity:activity-compose:1.8.2")
implementation(platform("androidx.compose:compose-bom:2024.02.00"))
// implementation(platform("androidx.compose:compose-bom:2023.06.01"))
implementation("androidx.activity:activity-compose:1.9.0")
implementation("androidx.compose.ui:ui")
implementation("androidx.compose.ui:ui-graphics")
implementation("androidx.compose.ui:ui-tooling-preview")
implementation("androidx.compose.material3:material3:1.2.0")
implementation("androidx.compose.material3:material3:1.2.1")

// Room DB
implementation("androidx.room:room-runtime:2.6.1")
Expand All @@ -129,14 +128,14 @@ dependencies {
implementation("io.coil-kt:coil-compose:2.5.0")
implementation("io.coil-kt:coil-gif:2.5.0")

implementation(project(":composeblurhash")) // Blurhash support for Compose

implementation("io.github.aghajari:LazySwipeCards:1.0.1") // Swipeable Cards
// implementation(project(":LazySwipeCards"))
implementation("androidx.compose.foundation:foundation:1.6.1") // For... what?
implementation("androidx.navigation:navigation-compose:2.7.7") // For NavController support
implementation("org.burnoutcrew.composereorderable:reorderable:0.7.0") // For Modifier.reorderable

// val composeBom = platform("androidx.compose:compose-bom:2023.10.01")
// implementation(composeBom)
implementation("androidx.compose.material:material-icons-extended") // Material icons (all)

implementation("com.airbnb.android:lottie-compose:6.2.0") // Lottie
Expand All @@ -151,7 +150,7 @@ dependencies {

implementation("com.google.accompanist:accompanist-permissions:0.33.2-alpha") // Accompanist Permissions

implementation("ch.acra:acra-http:5.11.3") // Android Crash Reports via HTTP
implementation("ch.acra:acra-mail:5.11.3") // Android Crash Reports via HTTP

// Dev dependencies
testImplementation("junit:junit:4.13.2")
Expand Down
45 changes: 1 addition & 44 deletions app/proguard-rules.pro
Original file line number Diff line number Diff line change
Expand Up @@ -7,47 +7,4 @@

-keepclassmembers class * extends androidx.datastore.preferences.protobuf.GeneratedMessageLite {
<fields>;
}

-dontwarn com.squareup.javapoet.AnnotationSpec$Builder
-dontwarn com.squareup.javapoet.AnnotationSpec
-dontwarn com.squareup.javapoet.ClassName
-dontwarn javax.lang.model.SourceVersion
-dontwarn javax.lang.model.element.AnnotationMirror
-dontwarn javax.lang.model.element.AnnotationValue
-dontwarn javax.lang.model.element.AnnotationValueVisitor
-dontwarn javax.lang.model.element.Element
-dontwarn javax.lang.model.element.ElementKind
-dontwarn javax.lang.model.element.ElementVisitor
-dontwarn javax.lang.model.element.ExecutableElement
-dontwarn javax.lang.model.element.Modifier
-dontwarn javax.lang.model.element.Name
-dontwarn javax.lang.model.element.PackageElement
-dontwarn javax.lang.model.element.QualifiedNameable
-dontwarn javax.lang.model.element.TypeElement
-dontwarn javax.lang.model.element.TypeParameterElement
-dontwarn javax.lang.model.element.VariableElement
-dontwarn javax.lang.model.type.ArrayType
-dontwarn javax.lang.model.type.DeclaredType
-dontwarn javax.lang.model.type.ErrorType
-dontwarn javax.lang.model.type.ExecutableType
-dontwarn javax.lang.model.type.IntersectionType
-dontwarn javax.lang.model.type.NoType
-dontwarn javax.lang.model.type.NullType
-dontwarn javax.lang.model.type.PrimitiveType
-dontwarn javax.lang.model.type.TypeKind
-dontwarn javax.lang.model.type.TypeMirror
-dontwarn javax.lang.model.type.TypeVariable
-dontwarn javax.lang.model.type.TypeVisitor
-dontwarn javax.lang.model.type.WildcardType
-dontwarn javax.lang.model.util.AbstractElementVisitor8
-dontwarn javax.lang.model.util.ElementFilter
-dontwarn javax.lang.model.util.Elements
-dontwarn javax.lang.model.util.SimpleAnnotationValueVisitor8
-dontwarn javax.lang.model.util.SimpleElementVisitor8
-dontwarn javax.lang.model.util.SimpleTypeVisitor8
-dontwarn javax.lang.model.util.Types
-dontwarn javax.tools.Diagnostic$Kind
-dontwarn javax.tools.FileObject
-dontwarn javax.tools.JavaFileManager$Location
-dontwarn javax.tools.StandardLocation
}
Original file line number Diff line number Diff line change
@@ -1,13 +1,11 @@
package net.blusutils.smupe

import androidx.test.platform.app.InstrumentationRegistry
import androidx.test.ext.junit.runners.AndroidJUnit4

import androidx.test.platform.app.InstrumentationRegistry
import org.junit.Assert.assertEquals
import org.junit.Test
import org.junit.runner.RunWith

import org.junit.Assert.*

/**
* Instrumented test, which will execute on an Android device.
*
Expand Down
1 change: 1 addition & 0 deletions app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>

<application
android:name=".SmupeApplication"
android:allowBackup="true"
android:dataExtractionRules="@xml/data_extraction_rules"
android:fullBackupContent="@xml/backup_rules"
Expand Down
12 changes: 12 additions & 0 deletions app/src/main/java/net/blusutils/smupe/CurrentApiDefParams.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package net.blusutils.smupe

import net.blusutils.smupe.common.api_definitions.domain.model.image.source.BaseImageSource
import net.blusutils.smupe.logic.api_definitions.data.network.service.implementation.Gallery

object CurrentApiDefParams {
var currentApi: BaseImageSource? = null
var currentSearchQuery = ""
var dynamicRepos = mutableListOf<BaseImageSource>(
net.blusutils.smupe.common.api_definitions.data.network.service.CatApi, Gallery
)
}
16 changes: 10 additions & 6 deletions app/src/main/java/net/blusutils/smupe/ErrorActivity.kt
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package net.blusutils.smupe

import android.os.Bundle
import android.util.Log
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.foundation.layout.Column
Expand All @@ -14,14 +15,16 @@ import androidx.compose.material3.*
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.scale
import androidx.compose.ui.unit.dp
import net.blusutils.smupe.ui.SmupeTheme
import net.blusutils.smupe.presentation.theme.SmupeTheme
import org.acra.ktx.sendWithAcra

class ErrorActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)

val thread = intent.extras?.getString("thread") ?: "unknown"
val exception = intent.extras?.getString("exception") ?: "unknown"
val exception = intent.extras?.getString("exception") ?: ""
Log.d("ERR", exception)

setContent {
SmupeTheme {
Expand All @@ -31,27 +34,28 @@ class ErrorActivity : ComponentActivity() {
},
icon = { Icon(Icons.Default.BugReport, "Bug icon", Modifier.scale(1.2f)) },
dismissButton = { TextButton(onClick = { this.finish() }) { Text("Exit") } },
confirmButton = { Button({}) { Text("Report") } },
confirmButton = { Button({ Exception(exception).sendWithAcra(); this.finish() }) { Text("Report") } },
title = {
Text(getString(R.string.well_that_s_a_bug))
},
text = {
Column(
Modifier
.fillMaxHeight(.5f)
.fillMaxHeight(.7f)
.verticalScroll(rememberScrollState())
.padding(4.dp)) {
Text(getString(R.string.unhandled_error_dialog_message))
Text("~~~~~~")
Text("Unhandled exception occurred in $thread thread.")
Text("The exception stacktrace shown below:")
if (exception.isNotBlank())
Text("The exception stacktrace shown below:")
Card(
Modifier
.padding(4.dp)
.fillMaxHeight(.9f)
) {
Text(exception,
Modifier
.verticalScroll(rememberScrollState())
.padding(8.dp))
}
}
Expand Down
14 changes: 7 additions & 7 deletions app/src/main/java/net/blusutils/smupe/MainActivity.kt
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,12 @@ import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import jonathanfinerty.once.Once
import net.blusutils.smupe.data.image_sources.ApiDefFileWrapper.loadAllApiDefs
import net.blusutils.smupe.data.proto_datastore.SettingsProtobufSerializer
import net.blusutils.smupe.data.proto_datastore.settingsDataStore
import net.blusutils.smupe.data.room.AppDatabase.Companion.initDb
import net.blusutils.smupe.ui.App
import net.blusutils.smupe.ui.SmupeTheme
import net.blusutils.smupe.logic.api_definitions.domain.utils.implementation.AndroidApiDefWrapper
import net.blusutils.smupe.logic.db.database.AppDatabase.Companion.initDb
import net.blusutils.smupe.logic.settings.domain.util.SettingsProtobufSerializer
import net.blusutils.smupe.logic.settings.domain.util.settingsDataStore
import net.blusutils.smupe.presentation.theme.SmupeTheme
import net.blusutils.smupe.presentation.ui.root.App
import java.lang.Thread.UncaughtExceptionHandler

class MainActivity : AppCompatActivity(), UncaughtExceptionHandler {
Expand All @@ -25,7 +25,7 @@ class MainActivity : AppCompatActivity(), UncaughtExceptionHandler {

this.initDb()

this.loadAllApiDefs()
AndroidApiDefWrapper(this).loadAllApiDefs()

Once.initialise(this)

Expand Down
27 changes: 27 additions & 0 deletions app/src/main/java/net/blusutils/smupe/SmupeApplication.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package net.blusutils.smupe

import android.app.Application
import android.content.Context
import android.util.Log
import org.acra.ACRA
import org.acra.config.mailSender
import org.acra.data.StringFormat
import org.acra.ktx.initAcra

class SmupeApplication : Application() {
override fun attachBaseContext(base: Context) {
super.attachBaseContext(base)
Log.d("SMUPEAPP","works")
ACRA.DEV_LOGGING = true
initAcra {
//core configuration:
buildConfigClass = BuildConfig::class.java
reportFormat = StringFormat.JSON
mailSender {
mailTo = "egorbron@inbox.ru"
reportFileName = "smupe_crash_report.txt"
body = "Test"
}
}
}
}
Loading