为啥要到 WordPress 中写单页程序呢?在一个层面上其实 WordPress 不仅是一博客程序,同时也是一个建站程序,一个内容管理程序,能做的还有很多我这里就不一一列举了,那么我为啥要在 WordPress 使用 React JS 呢?这边我主要是提供一个大致的思路,其中的 React 可以用其他框架如 Vue 之类的代替…

WordPress 中能写什么单页程序呢?

这个就很多用途了,比如小工具类型的,自己软件的官网,软件的简单后台管理程序,反正一切能用网页实现的我认为都能利用 WordPress 中的页面功能实现,当然我只建议放一些简单的程序,复杂有必要的程序还是建议搭建一个新网站…

首先我们先了解一下原理(我这里只是抛砖引玉,希望有更好方法的小伙伴能告知我一下):利用 WordPress 中的页面发布功能,写入 JavaScript 将页面的 DOM 删除用 React 重新创建

整个流程:创建 loading 层覆盖以前的页面 body 内容 -> 加载 React 所需要的运行时 JS 文件 -> 创建新的 body 以及呈现 React 程序的 app div -> 删除 loading 层以及旧的 body 节点

怎么实现?我这里先直接贴出我的全部代码然后慢慢道出我的实现思路( 可以预览我的 demo 页面:https://bin.zmide.com/?page_id=503

<script rel="preload">
console.log("React 程序加载中…");
var loading = document.createElement("div");
loading.setAttribute("style", "min-width: 100vw;min-height: 100vh;background: #FFF;position: absolute;top: 0;bottom: 0;right: 0;left: 0;z-index: 9999999999;text-align: center;padding-top: 48vh;");
loading.innerHTML = `<h1>程序加载中…</h1>`;
document.getElementsByTagName("body")[0].appendChild(loading);
</script>

<script src="https://unpkg.com/react@16/umd/react.production.min.js" crossorigin=""></script>
<script src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js" crossorigin=""></script>
<script src="https://unpkg.com/babel-standalone@6/babel.min.js"></script>

<script type="text/babel">
var body = document.createElement("body");
var app = document.createElement("div");
app.setAttribute("id", "app");
body.appendChild(app);

// React APP
console.log('Hello Bin');
ReactDOM.render((
<button style={{margin: 20}} onClick={() => console.log("hello Bin")}>Like</button>
), app);

document.getElementsByTagName("html")[0].appendChild(body);
document.getElementsByTagName("body")[0].remove();
</script>

首先你需要到 WordPress 的管理后台添加一个页面( Page ),添加一个 自定义html 区块,将上面的代码贴进去保存发布就可以看到效果了,你也可以点击我上面提供的 demo 链接查看效果…

我们这里有 5 个 script 脚本,我将依次分析

<script rel="preload">
console.log("React 程序加载中…");
var loading = document.createElement("div");
loading.setAttribute("style", "min-width: 100vw;min-height: 100vh;background: #FFF;position: absolute;top: 0;bottom: 0;right: 0;left: 0;z-index: 9999999999;text-align: center;padding-top: 48vh;");
loading.innerHTML = `<h1>程序加载中…</h1>`;
document.getElementsByTagName("body")[0].appendChild(loading);
</script>

这第一个是 loading 页面,为啥需要这一层呢?原因是如果是直接创建的页面是包裹在你原来的博客详情页面的,所以我们需要把以前的页面全部删除,我尝试过直接删除但是这样如果我们下面的 JavaScript 代码还没执行就被删除了的话我们将不能实现代码的植入,我们得先用一个 loading 页面将其遮住,然后等我们的 React 程序加载完成后才能删除以前的这个 body ,所以这段代码主要就是生成一个全屏 loading 的 div 植入到旧的 body 中,loading.innerHTML 处可以自己实现其他加载动画或者什么的…

<script src="https://unpkg.com/react@16/umd/react.production.min.js" crossorigin=""></script>
<script src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js" crossorigin=""></script>
<script src="https://unpkg.com/babel-standalone@6/babel.min.js"></script>

这 3 个从外部导入 JavaScript 脚本的话就是 React JS 的运行环境(如果你要使用 Vue 实现或者要加载其他插件的 JavaScript 的话可以也可以在这里导入),这里我就不过多介绍了,有兴趣的小伙伴可以去看看 React 官网:https://zh-hans.reactjs.org/docs/add-react-to-a-website.html

<script type="text/babel">
var body = document.createElement("body");
var app = document.createElement("div");
app.setAttribute("id", "app");
body.appendChild(app);

// React APP
console.log('Hello Bin');
ReactDOM.render((
<button style={{margin: 20}} onClick={() => console.log("hello Bin")}>Like</button>
), app);

document.getElementsByTagName("html")[0].appendChild(body);
document.getElementsByTagName("body")[0].remove();
</script>

这里就是我们 React 程序的核心代码了,这里先是创建了一个新的 body 标签和 app div 标签,然后就是使用 ReactDOM.render 函数将 React APP 解析植入,最后就是删除旧的 body 由于 loading 页面也是包含在旧的 body 中所以会被一起删除,这样就能把我们的 React 程序加载出来了