Unity发布Windows平台后通过Advanced Installer制作安装包

Unity发布Windows平台后是一堆库资源,以及一个可执行的exe文件,并不是一个安装包,如果需要制作成安装包,需要再进一步打包,本篇文章介绍一个Advanced Installer的软件,专门用来制作Windows平台的安装包的。夸克网盘链接:https://pan.quark.cn/s/ae2f834ae61a

里面分别是三个文件,(第一个是Advanced Installer)第二第三个文件是自定义Advanced Installer事件的VS插件(如果需要用到,就需要安装这两个插件)。

在这里插入图片描述

一、打开后选择对应应用程序,新建项目
在这里插入图片描述

二、填写信息,分别是应用名称,版本,发布者,下方的控制面板根据需求是否开启(应用名称这边截图中填写的是属性变量对应的属性页面设置的)
在这里插入图片描述

属性页
在这里插入图片描述

三、导入需要打包的应用程序
在这里插入图片描述

四、设置开始菜单和桌面快捷方式(如有需求,没需求也可以不设置)选中需要创建的快捷方式的文件,右键创建,然后将快捷方式存放至桌面以及开始菜单中
在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

五、注册表的设置(如有需要,例如开机自启,其实就是把应用信息写入注册表,以及网页打开应用也是需要把信息写入注册表,网页打开应用后续会单独写一篇文章)
在这里插入图片描述

六、设置安装参数,安装文件夹指的是打开安装包选择安装位置时默认的位置,图片中指向的C盘的路径,下面的安装选项中:静默安装勾选后,就不会再跳出选择框等一些设置,直接会出现进度条进行安装,因此正常安装包需要勾选,除非你发布的是冷更新的安装包(后续会单独出一遍文章,写冷更新的操作),管理员身份运行,建议勾上,有些操作必须管理员权限才能操作,例如在注册表的Root中写入信息,必须要管理员权限才行,不勾选这种操作就不能正常执行。
在这里插入图片描述

七、设置构建信息,导出安装包保存位置,一个是exe的文件名,以及exe的图标
在这里插入图片描述

八、运行环境和启动条件(根据需求修改)
在这里插入图片描述

九、设置对话框,主题也就是对话框的不同默认的样式,对话框可以全部删除后自定义,主要可能涉及到的就是最后完成安装后,可能需要打开描述文件,或者直接启动应用程序,以及以管理员身份运行等。因此需要设置启动文件
在这里插入图片描述

十、最后设置自定义操作,为什么需要这个呢,是因为安装包,安装后如果需要卸载,他不会把文件夹下涉及到的文件全部卸载掉。因此需要自行编写一段删除文件的脚本。
在这里插入图片描述

十一、编写脚本文件流程(注意我这边使用的VS2022,C#编写的,也可以使用其他的,请自行研究)

这时候就需要用到开头提供的另外两个文件,安装完成后,打开VS新建项目(选择 C# Custom Action Project for WiX v3)注意如果那两个文件没安装成功,是不会显示该模块项目的。
在这里插入图片描述

在这里插入图片描述

十二、在CustomAction1中编写对应的执行事件即可,例如卸载应用后删除指定文件,那么怎么获取指定文件位置,可以通过注册表中的信息获取。注册表中的信息,怎么写入呢毕竟也不是一开始就有的,这时候就有两种写入方式,一种就是上方提到的在安装时设置好,直接写入即可,第二种代码运行后写入。(以下代码仅供参考,具体需要执行什么事件自行编写)

using Microsoft.Deployment.WindowsInstaller;
using Microsoft.Win32;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;

namespace AdvancedInstallerCustomAction
{
    public class CustomActions
    {
        [CustomAction]
        public static ActionResult CustomAction1(Session session)
        {
            session.Log("Begin CustomAction1");

            string manufacturer = session["Manufacturer"];
            string productName = session["ProductName"];

            using (RegistryKey handlerKey = Registry.CurrentUser.OpenSubKey($"SOFTWARE\\{manufacturer}\\{productName}"))
            {
                if (handlerKey != null)
                {
                    string value = (string)handlerKey.GetValue("Path");
                    if (!string.IsNullOrEmpty(value))
                    {
                        //var path = Path.Combine(value, productName);
                        RemoveSubDirectory(value, false);
                    }
                }            
            }

            var desktopShutout = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory), $"{productName}.lnk");
            RemoveFile(desktopShutout);

            var startMenuShutout = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Programs), productName);
            RemoveSubDirectory(startMenuShutout);

            return ActionResult.Success;
        }

        private static void RemoveFile(string path)
        {
            FileInfo file = new FileInfo(path);
            try
            {
                if (file.Exists)
                {
                    file.Delete();
                }
            }
            catch
            {
                return;
            }
        }

        private static void RemoveSubDirectory(string path,bool isDeleteRoot=true)
        {
            DirectoryInfo uper = new DirectoryInfo(path);
            try
            {
                if (uper.Exists)
                {
                    foreach (FileInfo subFile in uper.GetFiles())
                    {
                        subFile.Delete();
                    }
                    foreach (DirectoryInfo sub in uper.GetDirectories())
                    {
                        if (sub.GetFiles().Length > 0 || sub.GetDirectories().Length > 0)
                            RemoveSubDirectory(sub);
                    }

                    if (isDeleteRoot) uper.Delete(true);
                }
            }
            catch
            {
                return;
            }

        }

        private static void RemoveSubDirectory(DirectoryInfo uper, bool isDeleteRoot = true)
        {
            try
            {
                if (uper.Exists)
                {
                    foreach (FileInfo subFile in uper.GetFiles())
                    {
                        subFile.Delete();
                    }
                    foreach (DirectoryInfo sub in uper.GetDirectories())
                    {
                        if (sub.GetFiles().Length > 0 || sub.GetDirectories().Length > 0)
                            RemoveSubDirectory(sub);
                    }
                    if (isDeleteRoot) uper.Delete(true);
                }
            }
            catch
            {
                return;
            }
        }
    }
}

十三、生成dll,点击生成=》生成解决方案(或者点击重新生成解决方案)生成完后,下面会告诉你dll地址
在这里插入图片描述

十四、应用dll文件。点击添加自定义操作,通过DLL,选择刚生成的dll即可
在这里插入图片描述

十五、设置自定义操作执行时间和顺序,可以选中后设置,安装时执行,或者卸载时执行,并且可以在左侧调整执行顺序。
在这里插入图片描述

十六、构建安装包,回到产品详细页面,点击构建即可。构建完成后就能在你设置的输出位置看到构建好的安装包。
在这里插入图片描述

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

TenderRain。

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值