diff --git a/README.md b/README.md index 81382a1..809f4da 100644 --- a/README.md +++ b/README.md @@ -10,7 +10,8 @@ A Gemini protocol browser for Android based OS. Formerly called Två, and briefl ## Releases -See the project page on Öppenlab.net for latest download: [oppenlab.net/pr/ariane](https://oppenlab.net/pr/ariane/) +* See the project page on Öppenlab.net for latest download: [oppenlab.net/pr/ariane](https://oppenlab.net/pr/ariane/) +* Install on [Google Play](https://play.google.com/store/apps/details?id=oppen.gemini.ariane) ## Issue tracker diff --git a/app/build.gradle b/app/build.gradle index 8100b35..f154a3a 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -60,7 +60,6 @@ dependencies { kapt "androidx.room:room-compiler:$room_version" implementation "androidx.room:room-ktx:$room_version" - testImplementation 'junit:junit:4.13' androidTestImplementation 'androidx.test.ext:junit:1.1.2' androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0' diff --git a/app/proguard-rules.pro b/app/proguard-rules.pro index 481bb43..d45169b 100644 --- a/app/proguard-rules.pro +++ b/app/proguard-rules.pro @@ -18,4 +18,19 @@ # If you keep the line number information, uncomment this to # hide the original source file name. -#-renamesourcefileattribute SourceFile \ No newline at end of file +#-renamesourcefileattribute SourceFile + +-keep public class * implements com.bumptech.glide.module.GlideModule +-keep class * extends com.bumptech.glide.module.AppGlideModule { + (...); +} +-keep public enum com.bumptech.glide.load.ImageHeaderParser$** { + **[] $VALUES; + public *; +} +-keep class com.bumptech.glide.load.data.ParcelFileDescriptorRewinder$InternalRewinder { + *** rewind(); +} + +# for DexGuard only +# -keepresourcexmlelements manifest/application/meta-data@value=GlideModule \ No newline at end of file diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index f1f45be..9978b79 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -14,17 +14,19 @@ android:supportsRtl="true" android:theme="@style/AppTheme" android:networkSecurityConfig="@xml/network_security_config"> + + + + + + + + android:launchMode="singleTop"> - - - - - diff --git a/app/src/main/java/oppen/ariane/io/gemini/GeminiDatasource.kt b/app/src/main/java/oppen/ariane/io/gemini/GeminiDatasource.kt index de5cb7c..f56473f 100644 --- a/app/src/main/java/oppen/ariane/io/gemini/GeminiDatasource.kt +++ b/app/src/main/java/oppen/ariane/io/gemini/GeminiDatasource.kt @@ -193,7 +193,7 @@ class GeminiDatasource(val context: Context): Datasource { val bufferedReader = BufferedReader(headerInputReader) val headerLine = bufferedReader.readLine() - println("Tva: header: $headerLine") + println("Ariane: response header: $headerLine") val header = GeminiResponse.parseHeader(headerLine) @@ -246,8 +246,6 @@ class GeminiDatasource(val context: Context): Datasource { val filenameRegex = Regex("[^A-Za-z0-9]") val cacheFile = File(context.cacheDir, filenameRegex.replace(uri.path, "_")) - - when { cacheFile.exists() -> { when { diff --git a/app/src/main/java/oppen/ariane/ui/GemActivity.kt b/app/src/main/java/oppen/ariane/ui/GemActivity.kt index c88e540..3b2dd16 100644 --- a/app/src/main/java/oppen/ariane/ui/GemActivity.kt +++ b/app/src/main/java/oppen/ariane/ui/GemActivity.kt @@ -55,10 +55,13 @@ class GemActivity : AppCompatActivity() { private val model by viewModels() private lateinit var binding: ActivityGemBinding private lateinit var history: HistoryInterface - private val adapter = GemtextAdapter { uri, longTap, view -> + private val adapter = GemtextAdapter { adapter, uri, longTap, position: Int, view -> if(longTap){ - LinkPopup.show(view){ menuId -> + LinkPopup.show(view, uri){ menuId -> when (menuId) { + R.id.link_menu_load_image -> { + adapter.loadImage(position) + } R.id.link_menu_copy -> { Intent().apply { action = Intent.ACTION_SEND @@ -219,7 +222,15 @@ class GemActivity : AppCompatActivity() { model.request(address) } - checkIntentExtras() + checkIntentExtras(intent) + } + + override fun onNewIntent(intent: Intent?) { + super.onNewIntent(intent) + + intent?.let{ + checkIntentExtras(intent) + } } /** @@ -227,39 +238,23 @@ class GemActivity : AppCompatActivity() { * Checks intent to see if Activity was opened to handle selected text * */ - private fun checkIntentExtras() { + private fun checkIntentExtras(intent: Intent) { - //First check if there's a uri from a web link or other + //Via ProcessTextActivity from selected text in another app + if(intent.hasExtra("process_text")){ + val processText = intent.getStringExtra("process_text") + binding.addressEdit.setText(processText) + model.request(processText ?: "") + return + } + + //From clicking a gemini:// address val uri = intent.data if(uri != null){ binding.addressEdit.setText(uri.toString()) model.request(uri.toString()) return } - - //Then check if we've arrived here via some selected text - val processText = when { - Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && - intent.hasExtra(Intent.EXTRA_PROCESS_TEXT) -> { - intent.getCharSequenceExtra(Intent.EXTRA_PROCESS_TEXT).toString() - } - else -> { - null - } - } - processText?.let { text -> - if (text.startsWith("gemini://")) { - binding.addressEdit.setText(text) - model.request(text) - } else { - Snackbar.make(binding.root, "$text is not a valid Gemini address", Snackbar.LENGTH_SHORT).show() - } - } - } - - override fun onNewIntent(intent: Intent?) { - super.onNewIntent(intent) - intent?.data.toString().let{model.request(it)} } private fun showAlert(message: String) = runOnUiThread{ diff --git a/app/src/main/java/oppen/ariane/ui/GemtextAdapter.kt b/app/src/main/java/oppen/ariane/ui/GemtextAdapter.kt index e7f43f7..a537180 100644 --- a/app/src/main/java/oppen/ariane/ui/GemtextAdapter.kt +++ b/app/src/main/java/oppen/ariane/ui/GemtextAdapter.kt @@ -9,12 +9,15 @@ import kotlinx.android.synthetic.main.gemtext_code_block.view.* import kotlinx.android.synthetic.main.gemtext_link.view.* import kotlinx.android.synthetic.main.gemtext_text.view.gemtext_text_textview import oppen.ariane.R +import oppen.visible import java.net.URI -class GemtextAdapter(val onLink: (link: URI, longTap: Boolean, view: View?) -> Unit): RecyclerView.Adapter() { +class GemtextAdapter(val onLink: (adapter: GemtextAdapter, link: URI, longTap: Boolean, adapterPosition: Int, view: View?) -> Unit): RecyclerView.Adapter() { var lines = mutableListOf() + var imageIndexes = arrayListOf() + private val typeText = 0 private val typeH1 = 1 private val typeH2 = 2 @@ -110,14 +113,21 @@ class GemtextAdapter(val onLink: (link: URI, longTap: Boolean, view: View?) -> U holder.itemView.gemtext_text_link.setOnClickListener { val uri = getUri(lines[holder.adapterPosition]) println("User click link: $uri") - onLink(uri, false, null) + onLink(this, uri, false, holder.adapterPosition, null) } holder.itemView.gemtext_text_link.setOnLongClickListener {view -> val uri = getUri(lines[holder.adapterPosition]) println("User click link: $uri") - onLink(uri, true, view) + onLink(this, uri, true, holder.adapterPosition, view) true } + + if(imageIndexes.contains(holder.adapterPosition)){ + holder.itemView.gemtext_inline_image.visible(true) + + //todo - need to download the image... + + } } } } @@ -134,4 +144,9 @@ class GemtextAdapter(val onLink: (link: URI, longTap: Boolean, view: View?) -> U return null } + + fun loadImage(position: Int){ + imageIndexes.add(position) + notifyItemChanged(position) + } } \ No newline at end of file diff --git a/app/src/main/java/oppen/ariane/ui/ProcessTextActivity.kt b/app/src/main/java/oppen/ariane/ui/ProcessTextActivity.kt new file mode 100644 index 0000000..95b8e58 --- /dev/null +++ b/app/src/main/java/oppen/ariane/ui/ProcessTextActivity.kt @@ -0,0 +1,24 @@ +package oppen.ariane.ui + +import android.content.Intent +import android.os.Build +import android.os.Bundle +import androidx.appcompat.app.AppCompatActivity + +class ProcessTextActivity: AppCompatActivity() { + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + + val processText = when { + Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && intent.hasExtra(Intent.EXTRA_PROCESS_TEXT) -> intent.getCharSequenceExtra(Intent.EXTRA_PROCESS_TEXT).toString() + else -> null + } + + Intent(this, GemActivity::class.java).run { + putExtra("process_text", processText) + startActivity(this) + finish() + } + } +} \ No newline at end of file diff --git a/app/src/main/java/oppen/ariane/ui/modals_menus/LinkPopup.kt b/app/src/main/java/oppen/ariane/ui/modals_menus/LinkPopup.kt index f44355c..f5d6529 100644 --- a/app/src/main/java/oppen/ariane/ui/modals_menus/LinkPopup.kt +++ b/app/src/main/java/oppen/ariane/ui/modals_menus/LinkPopup.kt @@ -4,15 +4,23 @@ import android.view.MenuInflater import android.view.View import androidx.appcompat.widget.PopupMenu import oppen.ariane.R +import java.net.URI object LinkPopup { - fun show(view: View?, onMenuOption: (menuId: Int) -> Unit){ + fun show(view: View?, uri: URI, onMenuOption: (menuId: Int) -> Unit){ if(view != null) { val popup = PopupMenu(view.context, view) val inflater: MenuInflater = popup.menuInflater - inflater.inflate(R.menu.link_menu, popup.menu) + + val path = uri.toString().toLowerCase() + if(path.endsWith(".png") || path.endsWith(".jpg") || path.endsWith(".jpeg")){ + inflater.inflate(R.menu.image_link_menu, popup.menu) + }else{ + inflater.inflate(R.menu.link_menu, popup.menu) + } + popup.setOnMenuItemClickListener { menuItem -> onMenuOption(menuItem.itemId) true diff --git a/app/src/main/res/layout/gemtext_link.xml b/app/src/main/res/layout/gemtext_link.xml index f9e30b8..a0a9f45 100644 --- a/app/src/main/res/layout/gemtext_link.xml +++ b/app/src/main/res/layout/gemtext_link.xml @@ -1,6 +1,9 @@ - + \ No newline at end of file + android:layout_height="wrap_content" /> + + + \ No newline at end of file diff --git a/app/src/main/res/menu/image_link_menu.xml b/app/src/main/res/menu/image_link_menu.xml new file mode 100644 index 0000000..099518b --- /dev/null +++ b/app/src/main/res/menu/image_link_menu.xml @@ -0,0 +1,7 @@ + + + + + diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index a4b452a..2a107c7 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -4,6 +4,7 @@ Enter gemini:// address Enter search term Copy address + Load image About Address copied to clipboard Gemini address