imageviewer icon indicating copy to clipboard operation
imageviewer copied to clipboard

请问全屏时怎么延伸到状态栏呢

Open wyy-dev opened this issue 6 months ago • 21 comments

请问全屏预览是,怎么延伸到状态栏,现在是黑色的,返回时状态栏颜色会有延时

wyy-dev avatar May 18 '25 11:05 wyy-dev

如何展示全屏预览

binding.fullScreen.setOnClickListener {
    val isFullScreen = ViewerHelper.fullScreen
    ViewerHelper.fullScreen = !isFullScreen
    binding.fullScreen.text = if (!isFullScreen) "FullScreen(on)" else "FullScreen(off)"
    Config.TRANSITION_OFFSET_Y = if (!isFullScreen) 0 else statusBarHeight()
}

试试demo的这个功能,是问的这个问题吗?

iielse avatar May 21 '25 09:05 iielse

这个设置后没变化,预览图片还是没有延伸到状态栏,

wyy-dev avatar May 24 '25 14:05 wyy-dev

先看下现在的 demo 效果满足了需求吗?

iielse avatar May 26 '25 02:05 iielse

demo 功能能满足需要,但是展示全屏效果不生效,切换全屏后,还是没有延伸到状态栏

wyy-dev avatar May 27 '25 06:05 wyy-dev

确认以下历史问题是否和你的提问重叠。 如果是重复问题,先尝试 @1wayticket 提供的解决方案 https://github.com/iielse/imageviewer/issues/148 https://github.com/iielse/imageviewer/issues/103

iielse avatar May 28 '25 08:05 iielse

import android.annotation.SuppressLint
import android.app.Activity
import android.view.View
import android.view.WindowManager

// Powered by [email protected]
// https://github.com/mikepenz/MaterialDrawer/issues/254
// https://github.com/laobie/StatusBarUtil/blob/master/library/src/main/java/com/jaeger/library/StatusBarUtil.java
object StatusBarUtils {
    private const val SYSTEM_UI_FLAG_LIGHT_STATUS_BAR = 0x00002000
    private const val SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR = 0x00000010

    private fun setWindowFlag(
        activity: Activity,
        bits: Int,
        on: Boolean
    ) {
        val win = activity.window
        val winParams = win.attributes
        if (on) {
            winParams.flags = winParams.flags or bits
        } else {
            winParams.flags = winParams.flags and bits.inv()
        }
        win.attributes = winParams
    }

    @SuppressLint("ObsoleteSdkInt")
    fun update(
        activity: Activity,
        statusBarTranslucent: Boolean,
        navigationBarTranslucent: Boolean,
        statusBarLightMode: Boolean, // lightMode -> darkIcon
        navigationBarLightMode: Boolean
    ) {

        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.KITKAT &&
            android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.LOLLIPOP
        ) {
            if (statusBarTranslucent) {
                setWindowFlag(activity, WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS, true)
            }
            if (navigationBarTranslucent) {
                setWindowFlag(
                    activity,
                    WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION,
                    true
                )
            }
        }
        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.LOLLIPOP) {
            if (statusBarTranslucent) {
                setWindowFlag(activity, WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS, false)
            }
            activity.window.statusBarColor = android.graphics.Color.TRANSPARENT

            if (navigationBarTranslucent) {
                setWindowFlag(
                    activity,
                    WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION,
                    false
                )
            }
            activity.window.navigationBarColor = android.graphics.Color.TRANSPARENT
            if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.P) {
                activity.window.navigationBarDividerColor = android.graphics.Color.TRANSPARENT
            }
        }

        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.LOLLIPOP) {
            activity.windowDecorView?.systemUiVisibility =
                View.SYSTEM_UI_FLAG_VISIBLE.let { 
                    var result = it
                    if (statusBarTranslucent) result =
                        result or View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
                    if (navigationBarTranslucent) result =
                        result or View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
                    if (statusBarLightMode) result = result or SYSTEM_UI_FLAG_LIGHT_STATUS_BAR

                    if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.M) {
                        if (statusBarLightMode) result =
                            result or SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR
                    }

                    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
                        if (navigationBarLightMode) result =
                            result or View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR
                    }
                    result
                }
        }
    }

    private val Activity.windowDecorView: View? get() {
        return try {
            window.decorView
        } catch (e: Throwable) {
            e.printStackTrace()
            null
        }
    }
}

也可能是你自身就没支持延伸到状态栏. 这个问题并非框架的问题.

StatusBarUtils.update(
            this, statusBarTranslucent = true, navigationBarTranslucent = true,
            statusBarLightMode = false, navigationBarLightMode = false
        )

先用以上代码为你自身的Activity赋予全屏展示的能力.

iielse avatar Jun 07 '25 05:06 iielse

Image 大图查看区域延伸到状态栏

iielse avatar Jun 07 '25 05:06 iielse

StatusBarUtils.update( this, statusBarTranslucent = true, navigationBarTranslucent = true, statusBarLightMode = false, navigationBarLightMode = false ) 使用这个后主页面全屏了,但是弹出的预览页面还是没有延伸到状态栏

wyy-dev avatar Jun 11 '25 01:06 wyy-dev

https://github.com/user-attachments/assets/c0b6ab26-aa79-475b-8272-d7661659a3cd

wyy-dev avatar Jun 11 '25 01:06 wyy-dev

你提供的视频里,图片查看的时候,很明显,Activity延伸到状态栏的'特性' 被取消掉了。 从这个方面查找问题

iielse avatar Jun 11 '25 08:06 iielse

https://github.com/user-attachments/assets/04f612af-76ae-4167-97bb-91cdea7169a8

iielse avatar Jun 11 '25 08:06 iielse

我确定我没取消状态栏特性,我是直接用demo 只是把你上面发的代码添加上直接测试的,你要不用真机测试一下?

wyy-dev avatar Jun 11 '25 09:06 wyy-dev

我看你这个视频没有状态栏么,你只直接完全隐藏了?,不是设置的透明状态栏吗

wyy-dev avatar Jun 11 '25 09:06 wyy-dev

https://github.com/iielse/imageviewer/tree/demo-fullscreen

我将对应代码新增到了分支 demo-fullscreen 中. 点击demo下面的按钮 FullScreen(on),再唤起时图片展示区域就能延伸到状态栏。

iielse avatar Jun 12 '25 07:06 iielse

https://github.com/user-attachments/assets/9ebefa10-8187-4463-a1c3-8bb542e4b81f

我用新分支开始不行,我看你提供的demo中没有给主题,我用的主题是:

<style name="Theme.APP" parent="Base.Theme.APP" />

wyy-dev avatar Jun 13 '25 00:06 wyy-dev

我认为应该在DialogFragment中处理吧,而不是在activity中处理

wyy-dev avatar Jun 13 '25 00:06 wyy-dev

ImageViewerBuilder 提供了一个方法 setViewerFactory

你可以自己自定义继承 ImageViewerDialogFragment 比如demo中的 FullScreenImageViewerDialogFragment 代码片段 然后重写方法 onCreateDialog 来设置你自己需要的风格

class YourCustomImageViewerDialogFragment : ImageViewerDialogFragment() {
    ... 
    
    override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
        return Dialog(requireActivity(), YourDialogStyleHere).apply {
            setCanceledOnTouchOutside(true)
            window?.let(::setWindow)
        }
    }
    
    ...
}

iielse avatar Jun 13 '25 02:06 iielse

这个方法我也看了,但是一直没设置成功,怎么能改成跳转到Activity页面

wyy-dev avatar Jun 13 '25 02:06 wyy-dev

你可以对点击项目右上角的 Code clone 复制项目地址隆到到本地. 然后根据你自身的需求对代码进行定制化修改. 比如将 DialogFragment 改成 Activity 等

iielse avatar Jun 13 '25 08:06 iielse

你发送的视频.我在vivo真机和安卓模拟器上验证过. 效果和你不一样.能到状态栏. 目前问题就是如何. 能构建一个全屏展示的Dialog Window.

这个需求的核心在于对 Window 对象的处理。这方面涉及系统及版本差异,存在一定的兼容性问题。为了完美兼容各种 ROM,建议参考以下开源项目的思路和实现:

https://github.com/niorgai/StatusBarCompat https://github.com/laobie/StatusBarUtil

如果你解决了可以联系我. 后面我有时间的时候再看看

iielse avatar Jun 13 '25 08:06 iielse

https://github.com/iielse/imageviewer/tree/demo-fullscreen

我将新的代码增到了分支 demo-fullscreen 中. 你拉取代码后 再试试

iielse avatar Jun 13 '25 09:06 iielse

https://github.com/iielse/imageviewer/tree/demo-fullscreen

我将新的代码增到了分支 demo-fullscreen 中. 你拉取代码后 再试试

这个可以了,非常感谢

wyy-dev avatar Jun 17 '25 01:06 wyy-dev

可以了也麻烦抽时间留个视频效果看下把。 这个window的相关设置,估计涉及到手机,系统版本等兼容性问题,表现有差异。

iielse avatar Jun 18 '25 11:06 iielse

https://github.com/user-attachments/assets/5d7cde0e-9e45-48cf-a4db-441cf8208e50

已完美解决

wyy-dev avatar Jun 18 '25 11:06 wyy-dev