taffy-layout 1.0.1 → 1.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.ja-JP.md +264 -0
- package/README.md +2 -0
- package/README.zh-CN.md +264 -0
- package/package.json +1 -1
- package/pkg/README.md +2 -0
- package/pkg/taffy_wasm_bg.wasm +0 -0
package/README.ja-JP.md
ADDED
|
@@ -0,0 +1,264 @@
|
|
|
1
|
+
# Taffy Layout
|
|
2
|
+
|
|
3
|
+
[English](README.md) | [简体中文](README.zh-CN.md) | [日本語](README.ja-JP.md)
|
|
4
|
+
|
|
5
|
+
[](https://www.npmjs.com/package/taffy-layout)
|
|
6
|
+
[](https://opensource.org/licenses/MIT)
|
|
7
|
+
|
|
8
|
+
WebAssembly で高速に動作する [Taffy](https://github.com/DioxusLabs/taffy) レイアウトエンジンの JavaScript バインディング。CSS の Flexbox と Grid をほぼネイティブ性能で利用できます。
|
|
9
|
+
|
|
10
|
+
## ✨ 特徴
|
|
11
|
+
|
|
12
|
+
- **🚀 高性能**:WebAssembly によるレイアウト計算
|
|
13
|
+
- **📦 充実の CSS 対応**:Flexbox と CSS Grid を実装
|
|
14
|
+
- **🔧 カスタム計測**:テキスト/コンテンツ計測用コールバックに対応
|
|
15
|
+
- **📝 TypeScript 対応**:型定義を同梱
|
|
16
|
+
- **🌳 ツリー型 API**:複雑な階層構造にも効率的
|
|
17
|
+
- **💡 なじみやすい API**:CSS 風のプロパティ名と値
|
|
18
|
+
|
|
19
|
+
## 📦 インストール
|
|
20
|
+
|
|
21
|
+
```bash
|
|
22
|
+
npm install taffy-layout
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
## 🚀 クイックスタート
|
|
26
|
+
|
|
27
|
+
```typescript
|
|
28
|
+
import {
|
|
29
|
+
loadTaffy,
|
|
30
|
+
TaffyTree,
|
|
31
|
+
Style,
|
|
32
|
+
Display,
|
|
33
|
+
FlexDirection,
|
|
34
|
+
AlignItems,
|
|
35
|
+
} from "taffy-layout";
|
|
36
|
+
|
|
37
|
+
// WebAssembly モジュールを初期化
|
|
38
|
+
await loadTaffy();
|
|
39
|
+
|
|
40
|
+
// レイアウトツリーを作成
|
|
41
|
+
const tree = new TaffyTree();
|
|
42
|
+
|
|
43
|
+
// コンテナのスタイル
|
|
44
|
+
const containerStyle = new Style();
|
|
45
|
+
containerStyle.display = Display.Flex;
|
|
46
|
+
containerStyle.flexDirection = FlexDirection.Column;
|
|
47
|
+
containerStyle.alignItems = AlignItems.Center;
|
|
48
|
+
containerStyle.size = { width: 300, height: 200 };
|
|
49
|
+
containerStyle.padding = { left: 10, right: 10, top: 10, bottom: 10 };
|
|
50
|
+
|
|
51
|
+
// 子要素のスタイル
|
|
52
|
+
const childStyle = new Style();
|
|
53
|
+
childStyle.flexGrow = 1;
|
|
54
|
+
childStyle.size = { width: "100%", height: "auto" };
|
|
55
|
+
|
|
56
|
+
// ノードを生成
|
|
57
|
+
const child1 = tree.newLeaf(childStyle);
|
|
58
|
+
const child2 = tree.newLeaf(childStyle);
|
|
59
|
+
const container = tree.newWithChildren(
|
|
60
|
+
containerStyle,
|
|
61
|
+
BigUint64Array.from([child1, child2]),
|
|
62
|
+
);
|
|
63
|
+
|
|
64
|
+
// レイアウト計算
|
|
65
|
+
tree.computeLayout(container, { width: 300, height: 200 });
|
|
66
|
+
|
|
67
|
+
// 計算結果を取得
|
|
68
|
+
const containerLayout = tree.getLayout(container);
|
|
69
|
+
const child1Layout = tree.getLayout(child1);
|
|
70
|
+
const child2Layout = tree.getLayout(child2);
|
|
71
|
+
|
|
72
|
+
console.log(`Container: ${containerLayout.width}x${containerLayout.height}`);
|
|
73
|
+
console.log(
|
|
74
|
+
`Child 1: ${child1Layout.width}x${child1Layout.height} at (${child1Layout.x}, ${child1Layout.y})`,
|
|
75
|
+
);
|
|
76
|
+
console.log(
|
|
77
|
+
`Child 2: ${child2Layout.width}x${child2Layout.height} at (${child2Layout.x}, ${child2Layout.y})`,
|
|
78
|
+
);
|
|
79
|
+
```
|
|
80
|
+
|
|
81
|
+
## 📖 API リファレンス
|
|
82
|
+
|
|
83
|
+
### TaffyTree
|
|
84
|
+
|
|
85
|
+
レイアウトツリーを管理するメインクラス。
|
|
86
|
+
|
|
87
|
+
[ドキュメントを見る](./docs/classes/TaffyTree.md)
|
|
88
|
+
|
|
89
|
+
### Style
|
|
90
|
+
|
|
91
|
+
ノードのレイアウトプロパティを設定するオブジェクト。
|
|
92
|
+
|
|
93
|
+
[ドキュメントを見る](./docs/classes/Style.md)
|
|
94
|
+
|
|
95
|
+
### Layout
|
|
96
|
+
|
|
97
|
+
計算後のレイアウト結果 (読み取り専用)。
|
|
98
|
+
|
|
99
|
+
[ドキュメントを見る](./docs/classes/Layout.md)
|
|
100
|
+
|
|
101
|
+
### 列挙型
|
|
102
|
+
|
|
103
|
+
[ドキュメントを見る](./docs/index.md#enumerations)
|
|
104
|
+
|
|
105
|
+
### 型エイリアス
|
|
106
|
+
|
|
107
|
+
[ドキュメントを見る](./docs/index.md#type-aliases)
|
|
108
|
+
|
|
109
|
+
## 📐 カスタムテキスト計測
|
|
110
|
+
|
|
111
|
+
テキストなど動的な計測が必要な場合は、測定コールバックを渡せます。
|
|
112
|
+
|
|
113
|
+
```typescript
|
|
114
|
+
const tree = new TaffyTree();
|
|
115
|
+
const textStyle = new Style();
|
|
116
|
+
const rootNode = tree.newLeaf(new Style());
|
|
117
|
+
const measureTextWidth = (text: string) => text.length * 8;
|
|
118
|
+
const measureTextHeight = (text: string, width: number) => 20;
|
|
119
|
+
|
|
120
|
+
const textNode = tree.newLeafWithContext(textStyle, { text: "Hello, World!" });
|
|
121
|
+
|
|
122
|
+
tree.computeLayoutWithMeasure(
|
|
123
|
+
rootNode,
|
|
124
|
+
{ width: 800, height: "max-content" },
|
|
125
|
+
(known, available, node, context, style) => {
|
|
126
|
+
if (context?.text) {
|
|
127
|
+
// ここに独自のテキスト計測ロジックを実装
|
|
128
|
+
const width = measureTextWidth(context.text);
|
|
129
|
+
const height = measureTextHeight(context.text, available.width as number);
|
|
130
|
+
return { width, height };
|
|
131
|
+
}
|
|
132
|
+
return { width: 0, height: 0 };
|
|
133
|
+
},
|
|
134
|
+
);
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
## 🔧 エラーハンドリング
|
|
138
|
+
|
|
139
|
+
失敗する可能性のあるメソッドは `TaffyError` をスローします。try-catch で処理してください。
|
|
140
|
+
|
|
141
|
+
```typescript
|
|
142
|
+
try {
|
|
143
|
+
const tree = new TaffyTree();
|
|
144
|
+
const style = new Style();
|
|
145
|
+
const nodeId = tree.newLeaf(style);
|
|
146
|
+
console.log("Created node:", nodeId);
|
|
147
|
+
} catch (e) {
|
|
148
|
+
if (e instanceof TaffyError) {
|
|
149
|
+
console.error("Error:", e.message);
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
## 🌐 ブラウザ対応
|
|
155
|
+
|
|
156
|
+
WebAssembly をサポートするモダンブラウザで動作します。
|
|
157
|
+
|
|
158
|
+
- Chrome 57+
|
|
159
|
+
- Firefox 52+
|
|
160
|
+
- Safari 11+
|
|
161
|
+
- Edge 16+
|
|
162
|
+
|
|
163
|
+
## 📚 サンプル
|
|
164
|
+
|
|
165
|
+
### Flexbox 行レイアウト
|
|
166
|
+
|
|
167
|
+
```typescript
|
|
168
|
+
const rowStyle = new Style();
|
|
169
|
+
rowStyle.display = Display.Flex;
|
|
170
|
+
rowStyle.flexDirection = FlexDirection.Row;
|
|
171
|
+
rowStyle.justifyContent = JustifyContent.SpaceBetween;
|
|
172
|
+
rowStyle.gap = { width: 10, height: 0 };
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
### CSS Grid レイアウト
|
|
176
|
+
|
|
177
|
+
```typescript
|
|
178
|
+
import { Style, Display, GridAutoFlow } from "taffy-layout";
|
|
179
|
+
|
|
180
|
+
const gridStyle = new Style();
|
|
181
|
+
gridStyle.display = Display.Grid;
|
|
182
|
+
gridStyle.gridAutoFlow = GridAutoFlow.Row;
|
|
183
|
+
gridStyle.gap = { width: 10, height: 10 };
|
|
184
|
+
|
|
185
|
+
// グリッドアイテムの配置
|
|
186
|
+
const itemStyle = new Style();
|
|
187
|
+
itemStyle.gridRow = { start: 1, end: 3 }; // 2 行分
|
|
188
|
+
itemStyle.gridColumn = { start: 1, end: { span: 2 } }; // 2 列分
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
### グリッドテンプレート領域
|
|
192
|
+
|
|
193
|
+
```typescript
|
|
194
|
+
const gridStyle = new Style();
|
|
195
|
+
gridStyle.display = Display.Grid;
|
|
196
|
+
gridStyle.gridTemplateAreas = [
|
|
197
|
+
{ name: "header", rowStart: 1, rowEnd: 2, columnStart: 1, columnEnd: 4 },
|
|
198
|
+
{ name: "sidebar", rowStart: 2, rowEnd: 4, columnStart: 1, columnEnd: 2 },
|
|
199
|
+
{ name: "main", rowStart: 2, rowEnd: 4, columnStart: 2, columnEnd: 4 },
|
|
200
|
+
{ name: "footer", rowStart: 4, rowEnd: 5, columnStart: 1, columnEnd: 4 },
|
|
201
|
+
];
|
|
202
|
+
|
|
203
|
+
// 名前付きグリッドライン
|
|
204
|
+
gridStyle.gridTemplateRowNames = [
|
|
205
|
+
["header-start"],
|
|
206
|
+
["header-end", "content-start"],
|
|
207
|
+
["content-end", "footer-start"],
|
|
208
|
+
["footer-end"],
|
|
209
|
+
];
|
|
210
|
+
```
|
|
211
|
+
|
|
212
|
+
### 絶対配置
|
|
213
|
+
|
|
214
|
+
```typescript
|
|
215
|
+
const absoluteStyle = new Style();
|
|
216
|
+
absoluteStyle.position = Position.Absolute;
|
|
217
|
+
absoluteStyle.inset = { left: 10, top: 10, right: "auto", bottom: "auto" };
|
|
218
|
+
absoluteStyle.size = { width: 100, height: 50 };
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
### パーセントサイズ
|
|
222
|
+
|
|
223
|
+
```typescript
|
|
224
|
+
const percentStyle = new Style();
|
|
225
|
+
percentStyle.size = {
|
|
226
|
+
width: "50%", // 親幅の 50%
|
|
227
|
+
height: "100%", // 親高の 100%
|
|
228
|
+
};
|
|
229
|
+
```
|
|
230
|
+
|
|
231
|
+
### 置換要素のブロックレイアウト
|
|
232
|
+
|
|
233
|
+
```typescript
|
|
234
|
+
const imgStyle = new Style();
|
|
235
|
+
imgStyle.itemIsReplaced = true;
|
|
236
|
+
imgStyle.aspectRatio = 16 / 9; // 16:9
|
|
237
|
+
imgStyle.size = { width: "100%", height: "auto" };
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
## 🏗️ ソースからのビルド
|
|
241
|
+
|
|
242
|
+
```bash
|
|
243
|
+
# リポジトリを取得
|
|
244
|
+
git clone https://github.com/ByteLandTechnology/taffy-layout.git
|
|
245
|
+
cd taffy-layout
|
|
246
|
+
|
|
247
|
+
# 依存関係をインストール
|
|
248
|
+
npm install
|
|
249
|
+
|
|
250
|
+
# WebAssembly モジュールをビルド
|
|
251
|
+
npm run build
|
|
252
|
+
|
|
253
|
+
# テストを実行
|
|
254
|
+
npm test
|
|
255
|
+
```
|
|
256
|
+
|
|
257
|
+
## 📄 ライセンス
|
|
258
|
+
|
|
259
|
+
MIT License - 詳細は [LICENSE](LICENSE) を参照してください。
|
|
260
|
+
|
|
261
|
+
## 🙏 謝辞
|
|
262
|
+
|
|
263
|
+
- [Taffy](https://github.com/DioxusLabs/taffy) - 本プロジェクトがラップしている Rust 製レイアウトエンジン
|
|
264
|
+
- [wasm-bindgen](https://github.com/rustwasm/wasm-bindgen) - Rust/WebAssembly の相互運用を支えるツール
|
package/README.md
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
# Taffy Layout
|
|
2
2
|
|
|
3
|
+
[English](README.md) | [简体中文](README.zh-CN.md) | [日本語](README.ja-JP.md)
|
|
4
|
+
|
|
3
5
|
[](https://www.npmjs.com/package/taffy-layout)
|
|
4
6
|
[](https://opensource.org/licenses/MIT)
|
|
5
7
|
|
package/README.zh-CN.md
ADDED
|
@@ -0,0 +1,264 @@
|
|
|
1
|
+
# Taffy Layout
|
|
2
|
+
|
|
3
|
+
[English](README.md) | [简体中文](README.zh-CN.md) | [日本語](README.ja-JP.md)
|
|
4
|
+
|
|
5
|
+
[](https://www.npmjs.com/package/taffy-layout)
|
|
6
|
+
[](https://opensource.org/licenses/MIT)
|
|
7
|
+
|
|
8
|
+
基于 WebAssembly 的高性能 [Taffy](https://github.com/DioxusLabs/taffy) 布局引擎 JavaScript 绑定,将 CSS Flexbox 和 Grid 布局算法带到前端,接近原生性能。
|
|
9
|
+
|
|
10
|
+
## ✨ 特性
|
|
11
|
+
|
|
12
|
+
- **🚀 高性能**:WebAssembly 驱动的布局计算
|
|
13
|
+
- **📦 完整 CSS 支持**:实现 Flexbox 与 CSS Grid
|
|
14
|
+
- **🔧 自定义测量**:支持自定义文本/内容测量回调
|
|
15
|
+
- **📝 TypeScript 友好**:完整类型定义
|
|
16
|
+
- **🌳 基于树的 API**:适合复杂场景的高效树结构
|
|
17
|
+
- **💡 熟悉的 API**:类 CSS 的属性名称与取值
|
|
18
|
+
|
|
19
|
+
## 📦 安装
|
|
20
|
+
|
|
21
|
+
```bash
|
|
22
|
+
npm install taffy-layout
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
## 🚀 快速上手
|
|
26
|
+
|
|
27
|
+
```typescript
|
|
28
|
+
import {
|
|
29
|
+
loadTaffy,
|
|
30
|
+
TaffyTree,
|
|
31
|
+
Style,
|
|
32
|
+
Display,
|
|
33
|
+
FlexDirection,
|
|
34
|
+
AlignItems,
|
|
35
|
+
} from "taffy-layout";
|
|
36
|
+
|
|
37
|
+
// 初始化 WebAssembly 模块
|
|
38
|
+
await loadTaffy();
|
|
39
|
+
|
|
40
|
+
// 创建布局树
|
|
41
|
+
const tree = new TaffyTree();
|
|
42
|
+
|
|
43
|
+
// 容器样式
|
|
44
|
+
const containerStyle = new Style();
|
|
45
|
+
containerStyle.display = Display.Flex;
|
|
46
|
+
containerStyle.flexDirection = FlexDirection.Column;
|
|
47
|
+
containerStyle.alignItems = AlignItems.Center;
|
|
48
|
+
containerStyle.size = { width: 300, height: 200 };
|
|
49
|
+
containerStyle.padding = { left: 10, right: 10, top: 10, bottom: 10 };
|
|
50
|
+
|
|
51
|
+
// 子元素样式
|
|
52
|
+
const childStyle = new Style();
|
|
53
|
+
childStyle.flexGrow = 1;
|
|
54
|
+
childStyle.size = { width: "100%", height: "auto" };
|
|
55
|
+
|
|
56
|
+
// 创建节点
|
|
57
|
+
const child1 = tree.newLeaf(childStyle);
|
|
58
|
+
const child2 = tree.newLeaf(childStyle);
|
|
59
|
+
const container = tree.newWithChildren(
|
|
60
|
+
containerStyle,
|
|
61
|
+
BigUint64Array.from([child1, child2]),
|
|
62
|
+
);
|
|
63
|
+
|
|
64
|
+
// 计算布局
|
|
65
|
+
tree.computeLayout(container, { width: 300, height: 200 });
|
|
66
|
+
|
|
67
|
+
// 读取结果
|
|
68
|
+
const containerLayout = tree.getLayout(container);
|
|
69
|
+
const child1Layout = tree.getLayout(child1);
|
|
70
|
+
const child2Layout = tree.getLayout(child2);
|
|
71
|
+
|
|
72
|
+
console.log(`Container: ${containerLayout.width}x${containerLayout.height}`);
|
|
73
|
+
console.log(
|
|
74
|
+
`Child 1: ${child1Layout.width}x${child1Layout.height} at (${child1Layout.x}, ${child1Layout.y})`,
|
|
75
|
+
);
|
|
76
|
+
console.log(
|
|
77
|
+
`Child 2: ${child2Layout.width}x${child2Layout.height} at (${child2Layout.x}, ${child2Layout.y})`,
|
|
78
|
+
);
|
|
79
|
+
```
|
|
80
|
+
|
|
81
|
+
## 📖 API 参考
|
|
82
|
+
|
|
83
|
+
### TaffyTree
|
|
84
|
+
|
|
85
|
+
管理布局树的核心类。
|
|
86
|
+
|
|
87
|
+
[查看文档](./docs/classes/TaffyTree.md)
|
|
88
|
+
|
|
89
|
+
### Style
|
|
90
|
+
|
|
91
|
+
用于配置节点布局属性的对象。
|
|
92
|
+
|
|
93
|
+
[查看文档](./docs/classes/Style.md)
|
|
94
|
+
|
|
95
|
+
### Layout
|
|
96
|
+
|
|
97
|
+
只读的布局计算结果。
|
|
98
|
+
|
|
99
|
+
[查看文档](./docs/classes/Layout.md)
|
|
100
|
+
|
|
101
|
+
### 枚举
|
|
102
|
+
|
|
103
|
+
[查看文档](./docs/index.md#enumerations)
|
|
104
|
+
|
|
105
|
+
### 类型别名
|
|
106
|
+
|
|
107
|
+
[查看文档](./docs/index.md#type-aliases)
|
|
108
|
+
|
|
109
|
+
## 📐 自定义文本测量
|
|
110
|
+
|
|
111
|
+
对文本节点或需要动态测量的内容,可传入测量回调:
|
|
112
|
+
|
|
113
|
+
```typescript
|
|
114
|
+
const tree = new TaffyTree();
|
|
115
|
+
const textStyle = new Style();
|
|
116
|
+
const rootNode = tree.newLeaf(new Style());
|
|
117
|
+
const measureTextWidth = (text: string) => text.length * 8;
|
|
118
|
+
const measureTextHeight = (text: string, width: number) => 20;
|
|
119
|
+
|
|
120
|
+
const textNode = tree.newLeafWithContext(textStyle, { text: "Hello, World!" });
|
|
121
|
+
|
|
122
|
+
tree.computeLayoutWithMeasure(
|
|
123
|
+
rootNode,
|
|
124
|
+
{ width: 800, height: "max-content" },
|
|
125
|
+
(known, available, node, context, style) => {
|
|
126
|
+
if (context?.text) {
|
|
127
|
+
// 在这里实现文本测量逻辑
|
|
128
|
+
const width = measureTextWidth(context.text);
|
|
129
|
+
const height = measureTextHeight(context.text, available.width as number);
|
|
130
|
+
return { width, height };
|
|
131
|
+
}
|
|
132
|
+
return { width: 0, height: 0 };
|
|
133
|
+
},
|
|
134
|
+
);
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
## 🔧 错误处理
|
|
138
|
+
|
|
139
|
+
可能失败的方法会抛出 `TaffyError`。使用 try-catch 处理:
|
|
140
|
+
|
|
141
|
+
```typescript
|
|
142
|
+
try {
|
|
143
|
+
const tree = new TaffyTree();
|
|
144
|
+
const style = new Style();
|
|
145
|
+
const nodeId = tree.newLeaf(style);
|
|
146
|
+
console.log("Created node:", nodeId);
|
|
147
|
+
} catch (e) {
|
|
148
|
+
if (e instanceof TaffyError) {
|
|
149
|
+
console.error("Error:", e.message);
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
## 🌐 浏览器支持
|
|
155
|
+
|
|
156
|
+
支持所有具备 WebAssembly 的现代浏览器:
|
|
157
|
+
|
|
158
|
+
- Chrome 57+
|
|
159
|
+
- Firefox 52+
|
|
160
|
+
- Safari 11+
|
|
161
|
+
- Edge 16+
|
|
162
|
+
|
|
163
|
+
## 📚 示例
|
|
164
|
+
|
|
165
|
+
### Flexbox 行布局
|
|
166
|
+
|
|
167
|
+
```typescript
|
|
168
|
+
const rowStyle = new Style();
|
|
169
|
+
rowStyle.display = Display.Flex;
|
|
170
|
+
rowStyle.flexDirection = FlexDirection.Row;
|
|
171
|
+
rowStyle.justifyContent = JustifyContent.SpaceBetween;
|
|
172
|
+
rowStyle.gap = { width: 10, height: 0 };
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
### CSS Grid 布局
|
|
176
|
+
|
|
177
|
+
```typescript
|
|
178
|
+
import { Style, Display, GridAutoFlow } from "taffy-layout";
|
|
179
|
+
|
|
180
|
+
const gridStyle = new Style();
|
|
181
|
+
gridStyle.display = Display.Grid;
|
|
182
|
+
gridStyle.gridAutoFlow = GridAutoFlow.Row;
|
|
183
|
+
gridStyle.gap = { width: 10, height: 10 };
|
|
184
|
+
|
|
185
|
+
// 网格项定位
|
|
186
|
+
const itemStyle = new Style();
|
|
187
|
+
itemStyle.gridRow = { start: 1, end: 3 }; // 跨 2 行
|
|
188
|
+
itemStyle.gridColumn = { start: 1, end: { span: 2 } }; // 跨 2 列
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
### 网格区域模板
|
|
192
|
+
|
|
193
|
+
```typescript
|
|
194
|
+
const gridStyle = new Style();
|
|
195
|
+
gridStyle.display = Display.Grid;
|
|
196
|
+
gridStyle.gridTemplateAreas = [
|
|
197
|
+
{ name: "header", rowStart: 1, rowEnd: 2, columnStart: 1, columnEnd: 4 },
|
|
198
|
+
{ name: "sidebar", rowStart: 2, rowEnd: 4, columnStart: 1, columnEnd: 2 },
|
|
199
|
+
{ name: "main", rowStart: 2, rowEnd: 4, columnStart: 2, columnEnd: 4 },
|
|
200
|
+
{ name: "footer", rowStart: 4, rowEnd: 5, columnStart: 1, columnEnd: 4 },
|
|
201
|
+
];
|
|
202
|
+
|
|
203
|
+
// 命名网格线
|
|
204
|
+
gridStyle.gridTemplateRowNames = [
|
|
205
|
+
["header-start"],
|
|
206
|
+
["header-end", "content-start"],
|
|
207
|
+
["content-end", "footer-start"],
|
|
208
|
+
["footer-end"],
|
|
209
|
+
];
|
|
210
|
+
```
|
|
211
|
+
|
|
212
|
+
### 绝对定位
|
|
213
|
+
|
|
214
|
+
```typescript
|
|
215
|
+
const absoluteStyle = new Style();
|
|
216
|
+
absoluteStyle.position = Position.Absolute;
|
|
217
|
+
absoluteStyle.inset = { left: 10, top: 10, right: "auto", bottom: "auto" };
|
|
218
|
+
absoluteStyle.size = { width: 100, height: 50 };
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
### 百分比尺寸
|
|
222
|
+
|
|
223
|
+
```typescript
|
|
224
|
+
const percentStyle = new Style();
|
|
225
|
+
percentStyle.size = {
|
|
226
|
+
width: "50%", // 父级宽度的 50%
|
|
227
|
+
height: "100%", // 父级高度的 100%
|
|
228
|
+
};
|
|
229
|
+
```
|
|
230
|
+
|
|
231
|
+
### 替换元素的块级布局
|
|
232
|
+
|
|
233
|
+
```typescript
|
|
234
|
+
const imgStyle = new Style();
|
|
235
|
+
imgStyle.itemIsReplaced = true;
|
|
236
|
+
imgStyle.aspectRatio = 16 / 9; // 16:9 宽高比
|
|
237
|
+
imgStyle.size = { width: "100%", height: "auto" };
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
## 🏗️ 从源码构建
|
|
241
|
+
|
|
242
|
+
```bash
|
|
243
|
+
# 克隆仓库
|
|
244
|
+
git clone https://github.com/ByteLandTechnology/taffy-layout.git
|
|
245
|
+
cd taffy-layout
|
|
246
|
+
|
|
247
|
+
# 安装依赖
|
|
248
|
+
npm install
|
|
249
|
+
|
|
250
|
+
# 构建 WebAssembly 模块
|
|
251
|
+
npm run build
|
|
252
|
+
|
|
253
|
+
# 运行测试
|
|
254
|
+
npm test
|
|
255
|
+
```
|
|
256
|
+
|
|
257
|
+
## 📄 许可证
|
|
258
|
+
|
|
259
|
+
MIT License - 详见 [LICENSE](LICENSE)。
|
|
260
|
+
|
|
261
|
+
## 🙏 致谢
|
|
262
|
+
|
|
263
|
+
- [Taffy](https://github.com/DioxusLabs/taffy) - 本项目封装的 Rust 布局引擎
|
|
264
|
+
- [wasm-bindgen](https://github.com/rustwasm/wasm-bindgen) - Rust/WebAssembly 互操作工具
|
package/package.json
CHANGED
package/pkg/README.md
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
# Taffy Layout
|
|
2
2
|
|
|
3
|
+
[English](README.md) | [简体中文](README.zh-CN.md) | [日本語](README.ja-JP.md)
|
|
4
|
+
|
|
3
5
|
[](https://www.npmjs.com/package/taffy-layout)
|
|
4
6
|
[](https://opensource.org/licenses/MIT)
|
|
5
7
|
|
package/pkg/taffy_wasm_bg.wasm
CHANGED
|
Binary file
|