首页 > 代码库 > JavaScript设计模式 - 状态模式

JavaScript设计模式 - 状态模式

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>状态模式</title>
</head>
<body>
    <input type="button" value="download" id="download_button"></input>
    <input type="button" value="pause" id="pause_button"></input>
    <input type="button" value="resume" id="resume_button"></input>
    <br/>
    <br/>
    <br/>
    <input type="button" value="预安装" id="preins"></input>
    <input type="button" value="预安装失败" id="preinsf"></input>
    <input type="button" value="预安装成功" id="preinss"></input>
    <input type="button" value="安装" id="ins"></input>
    <input type="button" value="安装失败" id="insf"></input>
    <input type="button" value="安装成功" id="inss"></input>
    <br/>
    <br/>
    <br/>
    <br/>
    <br/>
    <br/>
    <input type="button" value="软件安装" id="soft"></input>




    <script type="text/javascript">


        // 基类状态
        class State {

            // 下载
            download() {
                throw new Error("子类必须要重写该方法!");
            }

            // 暂停
            pause() {
                throw new Error("子类必须要重写该方法!");
            }

            // 失败
            fail() {
                throw new Error("子类必须要重写该方法!");
            }

            // 完成
            finish() {
                throw new Error("子类必须要重写该方法!");
            }
        }

        // 准备状态
        class ReadyState extends State {

            constructor(download) {
                super();
                this._download = download;
            }

            // 点击下载后
            download() {
                this._download.setState(this._download.getDownloadingState());    // 把状态设置成 正在下载状态
                console.log("开始下载!");
            }

            pause() {
                console.error("还没开始下载怎么暂停呢!");
            }

            fail() {
                console.error("还没开始下载不可能失败!");
            }

            finish() {
                console.error("还没开始下载不会结束啊!");
            }
        }

        // 正在下载状态
        class DownloadingState extends State {

            constructor(download) {
                super();
                this._download = download;
            }

            download() {
                console.error("文件已经下载了!");
            }

            pause() {
                this._download.setState(this._download.getDownloadPausedState());    // 把状态设置成 暂停状态
                console.log("暂停(这里写暂停下载的代码)!");
            }

            fail() {
                this._download.setState(this._download.getDownloadedFailedState());    // 把状态设置成 失败状态
                console.log("下载失败(这里可以写下载时出错的异常逻辑)!");
            }

            finish() {
                this._download.setState(this._download.getDownloadedState());    // 把状态设置成 完成状态
                console.log("下载完成(这里可以写文件下载好后解压安装逻辑)!");
            }
        }

        // 暂停状态
        class DownloadPausedState extends State {

            constructor(download) {
                super();
                this._download = download;
            }

            download() {
                this._download.setState(this._download.getDownloadingState());    // 把状态设置成 正在下载中状态
                console.log("继续下载(这里可以写接着往下操作的逻辑)!");
            }

            pause() {
                console.error("已经暂停了!");
            }

            fail() {
                this._download.setState(this._download.getDownloadedFailedState());    // 把状态设置成 失败状态
                console.log("下载失败(这里可以写下载时出错的异常逻辑)!");
            }

            finish() {
                this._download.setState(this._download.getDownloadedState());    // 把状态设置成 完成状态
                console.log("下载完成(这里可以写文件下载好后解压安装逻辑)!");
            }
        }

        // 下载完成状态
        class DownloadedState extends State {

            constructor(download) {
                super();
                this._download = download;
            }

            download() {
                this._download.setState(this._download.getDownloadingState());     // 把状态设置成 正在下载状态
                console.log("文件重新下载中(这里可以安装逻辑)");
            }

            pause() {
                console.error("文件已完成,无需暂停!");
            }

            fail() {
                console.error("文件已完成,不可能失败!");
            }

            finish() {
                console.error("文件已完成!");
            }
        }

        // 下载失败状态
        class DownloadFailedState extends State {

            constructor(download) {
                super();
                this._download = download;
            }

            download() {
                this._download.setState(this._download.getDownloadingState());    // 把状态设置成 正在下载状态
                console.log("下载失败,重新下载中!");
            }

            pause() {
                console.error("下载失败,怎能暂停!");
            }

            fail() {
                console.error("已经下载失败啦!");
            }

            finish() {
                console.error("下载已经失败了,怎么会完成呢!");
            }
        }

        class Download {
            constructor() {
                this.state = new ReadyState(this);    // 最开始的时候就是准备状态
            }

            setState(state) {
                this.state = state;
            }

            download() {
                this.state.download();
            }

            pause() {
                this.state.pause();
            }

            fail() {
                this.state.fail();
            }

            finish() {
                this.state.finish();
            }

            getReadyState() {
                return new ReadyState(this);
            }

            getDownloadingState() {
                return new DownloadingState(this);
            }

            getDownloadPausedState() {
                return new DownloadPausedState(this);
            }

            getDownloadedState() {
                return new DownloadedState(this);
            }

            getDownloadedFailedState() {
                return new DownloadFailedState(this);
            }
        }


        // 安装基类状态
        class InstallState {

            // 预安装(解压或者其他操作)
            preInstall() {
                throw new Error("子类必须要重写该方法!");
            }

            // 预安装失败
            preInstallFail() {
                throw new Error("子类必须要重写该方法!");
            }

            // 预安装完成
            preInstallFinish() {
                throw new Error("子类必须要重写该方法!");
            }

            // 安装
            install() {
                throw new Error("子类必须要重写该方法!");
            }

            // 安装失败
            installFail() {
                throw new Error("子类必须要重写该方法!");
            }

            // 安装完成
            installFinish() {
                throw new Error("子类必须要重写该方法!");
            }
        }

        // 准备预安装状态
        class ReadyPreInstallState extends InstallState {

            constructor(install) {
                super();
                this._install = install;
            }

            // 开始预安装
            preInstall() {
                this._install.setInstallState(this._install.getPreInstallingState());    // 把状态设置成 正在下载状态
                console.log("开始预安装!");
            }

            install() {
                console.error("还没开始预安装怎么直接安装呢!");
            }

            installFail() {
                console.error("还没开始预安装不可能安装失败!");
            }

            installFinish() {
                console.error("还没开始预安装不会安装结束啊!");
            }

            // 预安装失败
            preInstallFail() {
                console.log("还没开始预安装呢, 怎么会预安装失败呢!");
            }

            // 预安装完成
            preInstallFinish() {
                console.log("还没开始预安装呢, 怎么会安装成功!");
            }

        }

        // 正在预安装状态
        class PreInstallingState extends InstallState {

            constructor(install) {
                super();
                this._install = install;
            }

            preInstall() {
                console.error("已经在预安装了!");
            }

            install() {
                console.error("等待预安装完成!");
            }

            installFail() {
                console.error("预安装还没安装,怎么知晓会失败呢!");
            }

            installFinish() {
                console.error("预安装还没安装,怎么知晓会成功呢!");
            }

            // 预安装失败
            preInstallFail() {
                this._install.setInstallState(this._install.getPreInstallFailedState());    // 把状态设置成 预安装失败状态
                console.log("预安装失败(这里可以写预安装时出错的异常逻辑)!");
            }

            // 预安装完成
            preInstallFinish() {
                this._install.setInstallState(this._install.getPreInstallFinishState());    // 把状态设置成 预安装成功状态
                console.log("预安装成功(这里可以写安装的代码啦)!");
            }
        }

        // 预安装失败状态
        class PreInstallFailedState extends InstallState {

            constructor(install) {
                super();
                this._install = install;
            }

            preInstall() {
                this._install.setInstallState(this._install.getPreInstallingState());    // 把状态设置成 正在预安装状态
                console.log("重新预安装中!");
            }

            install() {
                console.error("预安装都失败了,还安装个毛线啊!");
            }

            installFail() {
                console.error("预安装已经安装失败了");
            }

            installFinish() {
                console.error("预安装已经安装失败了,怎么会成功呢!");
            }

            // 预安装失败
            preInstallFail() {
                console.log("预安装已经失败了!");
            }

            // 预安装完成
            preInstallFinish() {
                console.log("预安装已经失败了, 不会成功的!");
            }
        }

        // 预安装成功状态
        class PreInstallFinishState extends InstallState {

            constructor(install) {
                super();
                this._install = install;
            }

            preInstall() {
                this._install.setInstallState(this._install.getPreInstallingState());    // 把状态设置成 正在预安装状态
                console.log("重新预安装中!");
            }

            install() {
                this._install.setInstallState(this._install.getInstallingState());    // 把状态设置成 正在安装状态
                console.log("开始安装!");
            }

            installFail() {
                console.error("还没开始安装,怎么会失败!");
            }

            installFinish() {
                console.error("还没开始安装,怎么会完成呢!");
            }

            // 预安装失败
            preInstallFail() {
                console.log("预安装已经成功了,怎么会失败呢!");
            }

            // 预安装完成
            preInstallFinish() {
                console.log("预安装已经成功了!");
            }
        }

        // 正在安装状态
        class InstallingState extends InstallState {

            constructor(install) {
                super();
                this._install = install;
            }

            preInstall() {
                console.error("安装都开始了, 说明预安装已经好了!");
            }

            install() {
                console.error("已经在在安装中了!");
            }

            installFail() {
                this._install.setInstallState(this._install.getInstallFailedState());    // 把状态设置成 安装失败状态
                console.log("安装失败(这里可以写预安装时出错的异常逻辑)!");
            }

            installFinish() {
                this._install.setInstallState(this._install.getInstallFinishState());    // 把状态设置成 安装成功状态
                console.log("安装成功(这里可以写安装的代码啦)!");
            }

            // 预安装失败
            preInstallFail() {
                console.error("安装都开始了, 说明预安装已经好了,则不会安装失败!");
            }

            // 预安装完成
            preInstallFinish() {
                console.error("安装都开始了, 说明预安装已经好了!");
            }
        }

        // 安装失败状态
        class InstallFailedState extends InstallState {

            constructor(install) {
                super();
                this._install = install;
            }

            preInstall() {
                console.log("安装失败了,只能重新安装,不要调用我预安装!");
            }

            install() {
                this._install.setInstallState(this._install.getInstallingState());    // 把状态设置成 安装状态
                console.log("重新安装!");
            }

            installFail() {
                console.error("已经安装失败了,不要调用我");
            }

            installFinish() {
                console.error("已经安装失败了,自然不会成功的!");
            }

            // 预安装失败
            preInstallFail() {
                console.error("你安装失败和我预安装失败有毛的关系,点击安装试试去!");
            }

            // 预安装完成
            preInstallFinish() {
                console.error("你安装失败和我预安装成功有毛的关系,点击安装试试去!");
            }
        }

        // 安装成功状态
        class InstallFinishState extends InstallState {

            constructor(install) {
                super();
                this._install = install;
            }

            preInstall() {
                console.log("安装都成功了,不要调用我预安装!");
            }

            install() {
                this._install.setInstallState(this._install.getInstallingState());    // 把状态设置成 安装状态
                console.log("重新安装!");
            }

            installFail() {
                console.error("已经安装成功,怎么会失败呢");
            }

            installFinish() {
                console.error("已经安装成功,就不用再调用成功方法了!");
            }

            // 预安装失败
            preInstallFail() {
                console.error("安装都成功了,找我预安装失败也没用啊!");
            }

            // 预安装完成
            preInstallFinish() {
                console.error("安装都成功了,找我预安装完成也没用啊!");
            }
        }


        class Install {

            constructor() {
                this.installState = new ReadyPreInstallState(this);    // 最开始的时候就是准备状态
            }

            setInstallState(state) {
                this.installState = state;
            }

            preInstall() {
                this.installState.preInstall();
            }

            install() {
                this.installState.install();
            }

            installFail() {
                this.installState.installFail();
            }

            installFinish() {
                this.installState.installFinish();
            }

            // 预安装失败
            preInstallFail() {  
                this.installState.preInstallFail();
            }

            // 预安装完成
            preInstallFinish() {
                this.installState.preInstallFinish();
            }


            // 获取准备预安装状态
            getReadyPreInstallState() {
                return new ReadyPreInstallState(this);
            }

            // 获取正在预安装状态
            getPreInstallingState() {
                return new PreInstallingState(this);
            }

            // 获取预安装失败状态
            getPreInstallFailedState() {
                return new PreInstallFailedState(this);
            }

            // 获取预安装成功状态
            getPreInstallFinishState() {
                return new PreInstallFinishState(this);
            }

            // 获取正在安装状态
            getInstallingState() {
                return new InstallingState(this);
            }

            // 获取安装成功状态
            getInstallFinishState() {
                return new InstallFinishState(this);
            }

            // 获取安装失败状态
            getInstallFailedState() {
                return new InstallFailedState(this);
            }
        }

        class DownAndInstall {
            constructor() {
                this.state = new ReadyState(this);    // 最开始的时候就是准备状态
                this.installState = new ReadyPreInstallState(this);    // 最开始的时候就是准备状态
            }

            // 设置下载状态
            setState(state) {
                this.state = state;
            }

            // 下载
            download() {
                this.state.download();
            }

            // 暂停
            pause() {
                this.state.pause();
            }

            // 失败
            fail() {
                this.state.fail();
            }

            // 完成
            finish() {
                this.state.finish();
            }

            // 以下是获取下载状态

            getReadyState() {
                return new ReadyState(this);
            }

            getDownloadingState() {
                return new DownloadingState(this);
            }

            getDownloadPausedState() {
                return new DownloadPausedState(this);
            }

            getDownloadedState() {
                return new DownloadedState(this);
            }

            getDownloadedFailedState() {
                return new DownloadFailedState(this);
            }


            
            // 设置安装状态
            setInstallState(state) {
                this.installState = state;
            }

            // 预安装
            preInstall() {
                this.installState.preInstall();
            }

            // 安装
            install() {
                this.installState.install();
            }

            // 安装失败
            installFail() {
                this.installState.installFail();
            }

            // 安装成功
            installFinish() {
                this.installState.installFinish();
            }

            // 预安装失败
            preInstallFail() {  
                this.installState.preInstallFail();
            }

            // 预安装完成
            preInstallFinish() {
                this.installState.preInstallFinish();
            }



            // 以下是获取安装状态方法

            // 获取准备预安装状态
            getReadyPreInstallState() {
                return new ReadyPreInstallState(this);
            }

            // 获取正在预安装状态
            getPreInstallingState() {
                return new PreInstallingState(this);
            }

            // 获取预安装失败状态
            getPreInstallFailedState() {
                return new PreInstallFailedState(this);
            }

            // 获取预安装成功状态
            getPreInstallFinishState() {
                return new PreInstallFinishState(this);
            }

            // 获取正在安装状态
            getInstallingState() {
                return new InstallingState(this);
            }

            // 获取安装成功状态
            getInstallFinishState() {
                return new InstallFinishState(this);
            }

            // 获取安装失败状态
            getInstallFailedState() {
                return new InstallFailedState(this);
            }

        }








        var oDownload = new Download();
        var ins = new Install();

        function $(id) {
            return document.querySelector(id);
        }

        $("#download_button").onclick = function() {
            oDownload.download();
        }

        $("#pause_button").onclick = function() {
            oDownload.pause();
        }

        $("#resume_button").onclick = function() {
            oDownload.download();
        }




        $("#preins").onclick = function() {
            ins.preInstall();
        }
        $("#preinsf").onclick = function() {
            ins.preInstallFail();
        }
        $("#preinss").onclick = function() {
            ins.preInstallFinish();
        }
        $("#ins").onclick = function() {
            ins.install();
        }
        $("#insf").onclick = function() {
            ins.installFail();
        }
        $("#inss").onclick = function() {
            ins.installFinish();
        }




        // 模拟软件安装
        var downAndInstall = new DownAndInstall();
        var dom = $("#soft")

        dom.onclick = function() {
            dom.value = 文件下载中;
            downAndInstall.download();
            setTimeout(function() {
                if (0) {
                    downAndInstall.fail();
                    dom.value = 文件下载失败!;
                } else {
                    downAndInstall.finish();
                    dom.value = 文件下载成功!;
                    downAndInstall.preInstall();
                    dom.value = 文件预安装中!;
                    setTimeout(() => {
                        if(0) {
                            downAndInstall.preInstallFail();
                            dom.value = 文件预安装失败!;
                        } else {
                            downAndInstall.preInstallFinish();
                            dom.value = 文件预安装成功!;
                            downAndInstall.install();
                            dom.value = 文件正式安装中!;
                            setTimeout(() => {
                                if (0) {
                                    downAndInstall.installFail();
                                    dom.value = 文件正式安装失败!;
                                } else {
                                    downAndInstall.installFinish();
                                    dom.value = 文件正式安装成功!;
                                };

                            }, 5000);

                        };

                    }, 3000);
                };
                
            }, 5000);
        }



    </script>


</body>
</html>

 

JavaScript设计模式 - 状态模式