安卓图片对话框/弹出窗口

57

在Android应用程序中,是否可能只弹出/显示一张图片?类似于覆盖AlertDialog的常规视图,以便它仅包含一张图片而没有其他内容。

解决方案:通过@blessenm的帮助,我找到了答案。将活动掩盖为对话框似乎是理想的方法。以下是我使用的代码。可以按照启动新活动的方式随时调用此对话框样式的活动。

ImageDialog.java

public class ImageDialog extends Activity {

    private ImageView mDialog;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.your_dialog_layout);



        mDialog = (ImageView)findViewById(R.id.your_image);
        mDialog.setClickable(true);


        //finish the activity (dismiss the image dialog) if the user clicks 
        //anywhere on the image
        mDialog.setOnClickListener(new OnClickListener() {
        @Override
        public void onClick(View v) {
            finish();
        }
        });

    }
}

your_dialog_layout.xml

的翻译是:

你的对话框布局文件.xml

<?xml version="1.0" encoding="UTF-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/image_dialog_root" 
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:background="@android:color/transparent"
    android:gravity = "center">

    <ImageView
        android:id="@+id/your_image"  
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:src = "@drawable/your_image_drawable"/>

</FrameLayout>

为了实现这一点,您必须设置以下活动的样式:

styles.xml

  <style name="myDialogTheme" parent="@android:style/Theme.Dialog">
    <item name="android:windowNoTitle">true</item>
    <item name="android:windowFrame">@null</item>
    <item name="android:background">@android:color/transparent</item>
    <item name="android:windowBackground">@android:color/transparent</item>
    <item name="android:windowIsFloating">true</item>
    <item name="android:backgroundDimEnabled">false</item>
    <item name="android:windowContentOverlay">@null</item>
   </style>

最后一步是在清单文件中声明该样式的 Activity:

 <activity android:name=".ImageDialog" android:theme="@style/myDialogTheme" />

为什么在上述功能中使用Dialog样式的Activity而不是直接使用Dialog进行操作?这是有特定原因还是只是一种设计选择? - Avijeet
@Avijeet 这是一个有效的问题,当时的目标是展示一个浮动图像 - 这是几年前的事情了,当时视图自定义并不普遍。因此,将活动样式设置为对话框是有意义的。回想起来,我本可以使用 PopupWindow 或者自己编写自定义视图。 - Abhijit
你可以使用这个库来很容易地制作图片弹出窗口,而无需使用 Dialog。https://github.com/chathuralakmal/AndroidImagePopup - Im Batman
7个回答

69

没有xml:

public void showImage() {
    Dialog builder = new Dialog(this);
    builder.requestWindowFeature(Window.FEATURE_NO_TITLE);
    builder.getWindow().setBackgroundDrawable(
        new ColorDrawable(android.graphics.Color.TRANSPARENT));
    builder.setOnDismissListener(new DialogInterface.OnDismissListener() {
        @Override
        public void onDismiss(DialogInterface dialogInterface) {
            //nothing;
        }
    });

    ImageView imageView = new ImageView(this);
    imageView.setImageURI(imageUri);
    builder.addContentView(imageView, new RelativeLayout.LayoutParams(
            ViewGroup.LayoutParams.MATCH_PARENT, 
            ViewGroup.LayoutParams.MATCH_PARENT));
    builder.show();
}

1
我使用了这个,但是我什么也看不到? - Shailendra Madda
3
@ShylendraMadda 如果图片很大,可能无法正常工作。 - Oded Breiner
7
添加这行代码 Dialog dialog = new Dialog(context, android.R.style.Theme_Light),可以将对话框显示在全屏模式下,请参考 https://dev59.com/Vmkw5IYBdhLWcg3wDWPL - Weiyi

46

如果你只想使用普通的对话框,类似以下代码应该可以实现

Dialog settingsDialog = new Dialog(this);
settingsDialog.getWindow().requestFeature(Window.FEATURE_NO_TITLE);
settingsDialog.setContentView(getLayoutInflater().inflate(R.layout.image_layout
        , null));
settingsDialog.show();

image_layout.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="wrap_content" android:layout_height="wrap_content"
    android:orientation="vertical">
    <ImageView android:layout_width="wrap_content" 
        android:layout_height="wrap_content" android:src="YOUR IMAGE"/>
    <Button android:layout_width="wrap_content" android:layout_height="wrap_content"
        android:text="OK" android:onClick="dismissListener"/>
</LinearLayout>

1
感谢您的回复 - 这确实可以工作,但只能部分地实现。对话框仍将包含灰色背景和白色描边,类似于Android AlertDialog的样式。我的意图是使用图像替换传统的警报对话框。 - Abhijit
1
为了删除所有默认样式,您应该添加自己的样式并覆盖默认值。这可能会有所帮助。http://www.anddev.org/custom_theme_dialog___transparent_background-t7300.html - blessanm86
2
@Abhijit,您不必创建自定义样式,已经有一个没有标题或背景的样式可用,您可以使用DialogFragment.STYLE_NO_FRAME。 - Aldo Reyes
1
@Abhijit,如果您没有使用片段,则可以从普通的Dialog类中获取相同的样式。如果您使用支持库,则可以向后使用它。 - Aldo Reyes
我们如何更改图像源,以便每当我们按下自定义列表项时,我们就可以看到该项的图像。请帮忙。 - Uzumaki Naruto
显示剩余2条评论

3
请尝试以下操作:
它还具有图像缩放/放大功能。 步骤1:
compile 'com.github.chrisbanes.photoview:library:1.2.4'添加到您的build.gradle中。
步骤2:
添加以下xml:

custom_fullimage_dialoge.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
              android:id="@+id/layout_root" android:orientation="horizontal"
              android:layout_width="fill_parent" android:layout_height="fill_parent"
              android:padding="10dp">
    <ImageView android:id="@+id/fullimage" android:layout_width="fill_parent"
               android:layout_height="fill_parent">
    </ImageView>

    <TextView android:id="@+id/custom_fullimage_placename"
              android:layout_width="wrap_content" android:layout_height="fill_parent"
              android:textColor="#FFF">
    </TextView>
</LinearLayout>

步骤三:
private void loadPhoto(ImageView imageView, int width, int height) {

    final Dialog dialog = new Dialog(this);
    dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
    dialog.getWindow().setBackgroundDrawable(new ColorDrawable(android.graphics.Color.TRANSPARENT));
    //dialog.setContentView(R.layout.custom_fullimage_dialog);
    LayoutInflater inflater = (LayoutInflater) this.getSystemService(LAYOUT_INFLATER_SERVICE);
    View layout = inflater.inflate(R.layout.custom_fullimage_dialog,
            (ViewGroup) findViewById(R.id.layout_root));
    ImageView image = (ImageView) layout.findViewById(R.id.fullimage);
    image.setImageDrawable(imageView.getDrawable());
    image.getLayoutParams().height = height;
    image.getLayoutParams().width = width;
    mAttacher = new PhotoViewAttacher(image);
    image.requestLayout();
    dialog.setContentView(layout);
    dialog.show();

}

步骤4:
user_Image.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View v) {
        Display display = getWindowManager().getDefaultDisplay();
        int width = display.getWidth();
        int height = display.getHeight();
        loadPhoto(user_Image,width,height);
    }
});

3
您可以轻松地通过在Kotlin中创建Dialog Fragment来完成此操作:

BigImageDialog.kt

    class BigImageDialog():DialogFragment() {
    private var imageUrl = ""
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        arguments?.let {
            imageUrl = arguments.getString("url")
        }
    }
    override fun onCreateView(inflater: LayoutInflater?, container: ViewGroup?, savedInstanceState: Bundle?): View {
        val v = inflater!!.inflate(R.layout.dialog_big_image, container, false)
        this.dialog.window.requestFeature(Window.FEATURE_NO_TITLE)
        Picasso.get().load(imageUrl).into(v.bigImageView)
        return v
    }

    override fun onStart() {
        super.onStart()

        val dialog = dialog
        if (dialog != null) {
            dialog.window.setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)
        }
    }

    companion object {
        @JvmStatic
        fun newInstance(imageUrl: String) =
                BigImageDialog().apply {
                    arguments = Bundle().apply {
                        putString("url", imageUrl)
                    }
                }
    }
}

dialog_big_image.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.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">

    <ImageView
        android:id="@+id/bigImageView"
        android:layout_width="0dp"
        android:layout_height="0dp"
        android:scaleType="centerCrop"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.5"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />
</android.support.constraint.ConstraintLayout>

打开对话框:

"smallImageView".setOnClickListener { BigImageDialog.newInstance("image url").show(fragmentManager,"") }

1

有几种方法可以实现这个功能。但是,如果您希望图像看起来浮在现有活动之上,您可能需要在清单中定义一个具有android:theme="@style/Theme.Transparent"的活动。然后,设计您的布局只需将单个ImageView定位在屏幕中央即可。用户将不得不按返回按钮才能退出此操作,但这似乎是您想要的。

如果您希望它看起来像一个实际的对话框,您也可以使用Theme.Dialog样式的活动。或者,您可以使用对话框并自定义它。


非常感谢!我的想法是使用图像替换AlertDialog,但在用户点击它时消失。因此,实际上整个图像空间都像一个“确定”按钮一样工作。我将尝试使用您的第一个建议并回到您那里。另外,当您说自定义对话框时,是否意味着我要子类化对话框并覆盖方法? - Abhijit

1

更加灵活和推荐的方式是使用DialogFragment。如果您想支持3.0之前的版本,可以使用兼容库。


5
你能详细一些吗? - Abhijit
在此添加示例以更好地说明 - Anand Savjani

0

在经过三个小时的努力和帮助后,我找到了解决方案。

  1. 在需要点击图片或图标打开图片的单击事件中打开。

  2. 创建一个"对话框",以在ImageView中显示动态图像。

  3. 仅在单击事件中添加以下代码。

       holder.ivJobPhoto.setOnClickListener(view -> {              // THIS IS THE CLICK EVENT
    
            Dialog builder = new Dialog(mAcitvity);
            builder.requestWindowFeature(Window.FEATURE_NO_TITLE);
            builder.getWindow().setBackgroundDrawable(
                    new ColorDrawable(Color.TRANSPARENT));
            builder.setOnDismissListener(new DialogInterface.OnDismissListener() {
                @Override
                public void onDismiss(DialogInterface dialogInterface) {
                    //nothing;
                }
            });
            ImageView imageView = new ImageView(mAcitvity);
            PicassoTrustAll.getInstance(mAcitvity)
                    .load(imageUrls.get(position))
                    .placeholder(R.drawable.vector_app_logo_profile)
                    .into(imageView);
            builder.addContentView(imageView, new RelativeLayout.LayoutParams(550,550));
            builder.show(); 
        });
    

enter image description here

☻♥ 完成 保留代码。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接