Mithril.js 2 中文文档
什么是 Mithril.js?
Mithril.js 是一个现代客户端 JavaScript 框架,用于构建单页应用。 它体积小巧(gzip 压缩后 8.9 KiB),速度快,并开箱即用地提供路由和 XHR 工具。
下载大小
Mithril.js (8.9 KiB)Vue + Vue-Router + Vuex + fetch (40 KiB)React + React-Router + Redux + fetch (64 KiB)Angular (135 KiB)性能
Mithril.js (6.4 ms)Vue (9.8 ms)React (12.1 ms)Angular (11.5 ms)Mithril.js 被 Vimeo、Nike 等公司以及 Lichess 等开源平台所使用。
如果您是经验丰富的开发者,并且想了解 Mithril.js 与其他框架的比较,请参阅 框架比较 页面。
Mithril.js 支持 IE11、Firefox ESR 以及最新两个版本的 Firefox、Edge、Safari 和 Chrome。无需额外的 polyfill。
正在寻找 v1 文档?点击这里。
快速上手
试用 Mithril.js 的一个简单方法是从 CDN 引入,并按照本教程进行操作。本教程将涵盖大部分 API,只需 10 分钟。
让我们创建一个 HTML 文件来跟随学习:
<body>
<script src="https://unpkg.com/mithril/mithril.js"></script>
<script>
var root = document.body;
// your code goes here!
</script>
</body>
为了简化操作,您可以在此处直接试用 Mithril.js。这是一个预加载了 Mithril.js 的实时 playground,它也是用 Mithril 构建的。
var root = document.body;
// Your code here
m.mount(root, {
view: function () {
return m('h1', 'Try me out');
},
});
Hello world
让我们从一个最简单的例子开始:在屏幕上渲染一些文本。将下面的代码复制到您的文件中(这里的“复制”是指手动输入,这样您会学得更好):
var root = document.body;
m.render(root, 'Hello world');
现在,让我们将文本更改为其他内容。在上一行代码下添加此行代码:
m.render(root, 'My first app');
正如您所看到的,您可以使用相同的代码来创建和更新 HTML 内容。Mithril.js 会自动采用最高效的方式更新文本,而不是盲目地从头开始重新创建它。
实时示例
var root = document.body;
m.render(root, 'Hello World');
DOM 元素
让我们将文本放在 <h1>
标签中。
m.render(root, m('h1', 'My first app'));
m()
函数可用于描述您想要的任何 HTML 结构。如果需要为 <h1>
添加 class:
m('h1', { class: 'title' }, 'My first app');
如果想添加多个元素:
[m('h1', { class: 'title' }, 'My first app'), m('button', 'A button')];
以此类推:
m('main', [
m('h1', { class: 'title' }, 'My first app'),
m('button', 'A button'),
]);
实时示例
var root = document.body;
m.render(root, [
m('main', [
m('h1', { class: 'title' }, 'My first app'),
m('button', 'A button'),
]),
]);
注意:如果您喜欢使用 <html>
语法,可以通过 Babel 插件来实现。
// HTML syntax via Babel's JSX plugin
// 通过 Babel 的 JSX 插件实现的 HTML 语法
<main>
<h1 class="title">My first app</h1>
<button>A button</button>
</main>
组件
Mithril.js 组件是一个包含 view
函数的对象。以下是上面的代码作为一个组件:
var Hello = {
view: function () {
return m('main', [
m('h1', { class: 'title' }, 'My first app'),
m('button', 'A button'),
]);
},
};
要使用该组件,我们使用 m.mount
。
m.mount(root, Hello);
正如您所预期的,这样做会生成以下 HTML 结构:
<main>
<h1 class="title">My first app</h1>
<button>A button</button>
</main>
m.mount
函数类似于 m.render
,但它不仅会渲染一次 HTML,还会激活 Mithril.js 的自动重绘系统。为了理解这意味着什么,让我们添加一些事件。
var count = 0;
var Hello = {
view: function () {
return m('main', [
m('h1', { class: 'title' }, 'My first app'),
m(
'button',
{
onclick: function () {
count++;
},
},
count + ' clicks'
),
]);
},
};
m.mount(root, Hello);
我们为按钮定义了 onclick 事件,用于递增变量 count
。我们现在还在按钮标签中渲染该变量的值。
您现在可以通过单击按钮来更新按钮的文本。由于我们使用了 m.mount
,因此您无需手动调用 m.render
即可将 count
变量中的更改应用于 HTML;Mithril.js 会为您完成。
Mithril.js 在渲染更新方面非常高效,因为它只会更新 DOM 中真正需要改变的部分。例如,点击按钮时,只有按钮中的文本会被 Mithril.js 更新。
实时示例
var root = document.body;
var count = 0;
var Hello = {
view: function () {
return m('main', [
m(
'h1',
{
class: 'title',
},
'My first app'
),
m(
'button',
{
onclick: function () {
count++;
},
},
count + ' clicks'
),
]);
},
};
m.mount(root, Hello);
路由
路由就是在多页面应用中切换不同页面。
让我们添加一个启动页,该页面出现在我们的点击计数器之前。首先,我们为其创建一个组件:
var Splash = {
view: function () {
return m('a', { href: '#!/hello' }, 'Enter!');
},
};
正如您所见,此组件仅渲染一个指向 #!/hello
的链接。#!
部分被称为 hashbang (哈希井号),它是单页应用程序中常用的约定,用于指示其后的内容(/hello
部分)是路由路径。
现在应用包含多个页面,我们使用 m.route
而不是 m.mount
。
m.route(root, '/splash', {
'/splash': Splash,
'/hello': Hello,
});
m.route
函数同样具备 m.mount
的自动重绘功能,并且它还启用了 URL 感知;换句话说,它让 Mithril.js 知道当 URL 中出现 #!
时该如何处理。
"/splash"
紧跟在 root
之后,表示默认路由,即如果 URL 中的 hashbang 没有指向定义的路由之一(在我们的例子中为 /splash
和 /hello
),则 Mithril.js 会重定向到默认路由。因此,如果您在浏览器中打开该页面并且您的 URL 是 https://localhost
,那么您将被重定向到 https://localhost/#!/splash
。
此外,点击启动页上的链接,会跳转到之前创建的点击计数器页面。请注意,此时您的 URL 将变为 https://localhost/#!/hello
。您可以使用浏览器的后退和前进按钮来回导航到启动页面。
实时示例
var root = document.body;
var count = 0;
var Hello = {
view: function () {
return m('main', [
m(
'h1',
{
class: 'title',
},
'My first app'
),
m(
'button',
{
onclick: function () {
count++;
},
},
count + ' clicks'
),
]);
},
};
var Splash = {
view: function () {
return m(
'a',
{
href: '#!/hello',
},
'Enter!'
);
},
};
m.route(root, '/splash', {
'/splash': Splash,
'/hello': Hello,
});
XHR
XHR 是与服务器通信的一种方式。
让我们更改我们的点击计数器,使其将数据保存在服务器上。我们将使用 REM 作为服务器,这是一个专为本教程这样的示例应用设计的模拟 REST API。
首先,我们创建一个调用 m.request
的函数。url
指定一个表示资源的端点,method
指定我们正在采取的操作类型(通常使用 PUT 方法进行 upsert 操作),body
是我们发送到端点的有效负载,withCredentials
表示启用 cookie(REM API 的要求)。
var count = 0;
var increment = function () {
m.request({
method: 'PUT',
url: '//mithril-rem.fly.dev/api/tutorial/1',
body: { count: count + 1 },
withCredentials: true,
}).then(function (data) {
count = parseInt(data.count);
});
};
调用 increment
函数会对 /api/tutorial/1
端点执行 upsert 操作,数据为 {count: 1}
。此端点返回一个对象,该对象具有与发送给它的 count
值相同的 count
值。注意,count
变量只有在请求完成后才会更新,更新的值是服务器返回的响应值。
让我们替换组件中的事件处理函数,以调用 increment
函数而不是直接递增 count
变量:
var Hello = {
view: function () {
return m('main', [
m('h1', { class: 'title' }, 'My first app'),
m('button', { onclick: increment }, count + ' clicks'),
]);
},
};
现在点击按钮即可更新计数。
实时示例
var root = document.body;
var count = 0;
var increment = function () {
m.request({
method: 'PUT',
url: '//mithril-rem.fly.dev/api/tutorial/1',
body: { count: count + 1 },
withCredentials: true,
}).then(function (data) {
count = parseInt(data.count);
});
};
var Hello = {
view: function () {
return m('main', [
m(
'h1',
{
class: 'title',
},
'My first app'
),
m(
'button',
{
onclick: increment,
},
count + ' clicks'
),
]);
},
};
m.mount(root, Hello);
我们讲解了如何创建和更新 HTML,如何创建组件,单页应用程序的路由,以及如何通过 XHR 与服务器交互。
这些知识足以帮助您开始开发实际应用的前端。熟悉了 Mithril.js API 的基础知识后,请务必阅读简单的应用程序教程,该教程将引导您构建一个真实的应用程序。