Tentang codelab ini
1. Pengantar
Komponen Material (MDC) membantu developer menerapkan Desain Material. Dibuat oleh tim engineer dan desainer UX di Google, MDC memiliki banyak komponen UI yang indah dan fungsional serta tersedia untuk Android, iOS, web, dan Flutter.material.io/develop |
Web MDC dirancang untuk berintegrasi ke dalam framework front end apa pun dengan tetap menegakkan prinsip Desain Material. Codelab berikut memandu Anda dalam membangun Komponen React, yang menggunakan Web MDC sebagai fondasi. Prinsip yang dipelajari dalam codelab ini dapat diterapkan ke framework JavaScript apa pun.
Cara Web MDC dibuat
Lapisan JavaScript Web MDC terdiri dari tiga class per komponen: Komponen, Foundation, dan Adaptor. Pola ini memberi MDC Web fleksibilitas untuk berintegrasi dengan framework frontend.
Foundation berisi logika bisnis yang menerapkan Desain Material. Dasar ini tidak mereferensikan elemen HTML apa pun. Tindakan ini memungkinkan kita memisahkan logika interaksi HTML ke dalam Adapter. Foundation memiliki Adapter.
Adapter adalah antarmuka. Antarmuka Adaptor dirujuk oleh Foundation untuk menerapkan logika bisnis Desain Material. Anda dapat menerapkan Adapter di berbagai framework seperti Angular atau React. Implementasi Adaptor berinteraksi dengan struktur DOM.
Komponen memiliki Fondasi, dan perannya adalah untuk
- Implementasikan Adapter, menggunakan JavaScript non-framework, dan
- Sediakan metode publik yang melakukan proxy ke metode di Foundation.
Yang disediakan MDC Web
Setiap paket di Web MDC dilengkapi dengan Komponen, Foundation, dan Adaptor. Untuk membuat instance Komponen, Anda harus meneruskan elemen root ke metode konstruktor Komponen. Komponen menerapkan Adapter, yang berinteraksi dengan elemen DOM dan HTML. Komponen kemudian membuat instance Foundation, yang memanggil metode Adapter.
Untuk mengintegrasikan MDC Web ke dalam framework, Anda harus membuat Komponen sendiri dalam bahasa/sintaksis framework tersebut. Framework Komponen menerapkan Adapter Web MDC dan menggunakan Foundation MDC Web.
Yang akan Anda bangun
Codelab ini menunjukkan cara membuat Adapter kustom untuk menggunakan logika Foundation guna mencapai Komponen React Desain Material. Panduan ini mencakup topik lanjutan yang terdapat dalam artikel Mengintegrasikan ke Framework. React digunakan dalam codelab ini sebagai contoh framework, tetapi pendekatan ini dapat diterapkan ke framework lainnya.
Dalam codelab ini, Anda akan membangun Panel Aplikasi Atas dan membuat ulang halaman demo panel aplikasi atas. Tata letak halaman demo sudah disiapkan sehingga Anda dapat mulai bekerja di Panel Aplikasi Atas. Panel Aplikasi Atas akan mencakup:
- Ikon navigasi
- Item tindakan
- Ada 4 varian yang tersedia: varian Singkat, selalu diciutkan, tetap, dan jelas
Yang Anda butuhkan:
- Versi terbaru Node.js (yang dilengkapi dengan npm, pengelola paket JavaScript)
- Kode contoh (akan didownload pada langkah berikutnya)
- Pengetahuan dasar tentang HTML, CSS, JavaScript, dan React
Bagaimana Anda menilai tingkat pengalaman Anda dengan pengembangan web?
2. Menyiapkan lingkungan pengembangan
Mendownload aplikasi codelab awal
Aplikasi awal terletak di direktori material-components-web-codelabs-master/mdc-112/starter
.
...atau meng-clone codelab dari GitHub
Untuk meng-clone codelab ini dari GitHub, jalankan perintah berikut:
git clone https://github.com/material-components/material-components-web-codelabs
cd material-components-web-codelabs/mdc-112/starter
Menginstal dependensi project
Dari direktori awal material-components-web-codelabs/mdc-112/starter
, jalankan:
npm install
Anda akan melihat banyak aktivitas dan di akhir, terminal Anda akan menunjukkan penginstalan yang berhasil:
Menjalankan aplikasi awal
Dalam direktori yang sama, jalankan:
npm start
webpack-dev-server
akan dimulai. Arahkan browser ke http://localhost:8080/ untuk melihat halaman.
Berhasil! Kode awal untuk halaman Demo React Panel Aplikasi Teratas harus berjalan di browser Anda. Anda akan melihat dinding teks lorem ipsum, kotak Controls (kanan bawah), dan Panel Aplikasi Atas yang belum selesai:
Melihat kode dan project
Jika Anda membuka editor kode, direktori project akan terlihat seperti ini:
Buka file App.js
dan lihat metode render
yang menyertakan Komponen <TopAppBar>
:
App.js
render() {
const {isFixed, isShort, isRtl, isProminent, isAlwaysCollapsed, shouldReinit} = this.state;
return (
<section
dir={isRtl ? 'rtl' : 'ltr'}
className='mdc-typography'>
{
shouldReinit ? null :
<TopAppBar
navIcon={this.renderNavIcon()}
short={isShort}
prominent={isProminent}
fixed={isFixed}
alwaysCollapsed={isAlwaysCollapsed}
title='Mountain View, CA'
actionItems={this.actionItems}
/>
}
<div className={classnames('mdc-top-app-bar--fixed-adjust', {
'mdc-top-app-bar--short-fixed-adjust': isShort || isAlwaysCollapsed,
'mdc-top-app-bar--prominent-fixed-adjust': isProminent,
})}>
{this.renderDemoParagraphs()}
</div>
{this.renderControls()}
</section>
);
}
Ini adalah titik entri untuk TopAppBar
dalam aplikasi.
Buka file TopAppBar.js
yang merupakan class React Component
sederhana dengan metode render
:
TopAppBar.js
import React from 'react';
export default class TopAppBar extends React.Component {
render() {
return (
<header>
TOP APP BAR
</header>
);
}
}
3. Komposisi komponen
Di React, metode render
menghasilkan output HTML Komponen. Komponen Panel Aplikasi Atas akan merender tag <header />
, dan akan terdiri dari 2 bagian utama:
- Ikon navigasi dan bagian judul
- Bagian ikon tindakan
Jika ada pertanyaan tentang elemen yang membentuk Panel Aplikasi Atas, buka dokumentasi di GitHub.
Ubah metode render()
di TopAppBar.js
agar terlihat seperti ini:
render() {
const {
title,
navIcon,
} = this.props;
return (
<header
className={this.classes}
style={this.getMergedStyles()}
ref={this.topAppBarElement}
>
<div className='mdc-top-app-bar__row'>
<section className='mdc-top-app-bar__section mdc-top-app-bar__section--align-start'>
{navIcon ? navIcon : null}
<span className="mdc-top-app-bar__title">
{title}
</span>
</section>
{this.renderActionItems()}
</div>
</header>
);
}
Ada dua elemen bagian dalam HTML ini. Yang pertama berisi ikon dan judul navigasi. Yang kedua berisi ikon tindakan.
Selanjutnya, tambahkan metode renderActionItems
:
renderActionItems() {
const {actionItems} = this.props;
if (!actionItems) {
return;
}
return (
<section className='mdc-top-app-bar__section mdc-top-app-bar__section--align-end' role='toolbar'>
{/* need to clone element to set key */}
{actionItems.map((item, key) => React.cloneElement(item, {key}))}
</section>
);
}
Developer akan mengimpor TopAppBar
ke dalam aplikasi React-nya dan meneruskan ikon tindakan ke elemen TopAppBar
. Anda dapat melihat kode contoh yang melakukan inisialisasi TopAppBar
di App.js
.
Metode getMergedStyles
tidak ada, yang digunakan dalam metode render
. Tambahkan metode JavaScript berikut ke class TopAppBar
:
getMergedStyles = () => {
const {style} = this.props;
const {style: internalStyle} = this.state;
return Object.assign({}, internalStyle, style);
}
this.classes
juga tidak ada di metode render
, tetapi akan dibahas di bagian selanjutnya. Selain metode pengambil yang tidak ada, this.classes
, masih ada bagian TopAppBar
yang perlu Anda terapkan sebelum Panel Aplikasi Atas dapat dirender dengan benar.
Bagian dari Komponen React yang masih belum ada di Panel Aplikasi Atas adalah:
- Fondasi yang diinisialisasi
- Metode adaptor untuk diteruskan ke fondasi
- Markup JSX
- Pengelolaan varian (tetap, singkat, selalu diciutkan, terlihat)
Pendekatan
- Terapkan metode Adapter.
- Lakukan inisialisasi Foundation di
componentDidMount
. - Panggil metode Foundation.destroy di
componentWillUnmount
. - Menetapkan pengelolaan varian melalui metode pengambil yang menggabungkan nama class yang sesuai.
4. Mengimplementasikan metode Adaptor
Komponen TopAppBar
JS non-framework menerapkan metode Adapter berikut (tercantum secara detail di sini):
hasClass()
addClass()
removeClass()
registerNavigationIconInteractionHandler()
deregisterNavigationIconInteractionHandler()
notifyNavigationIconClicked()
setStyle()
getTopAppBarHeight()
registerScrollHandler()
deregisterScrollHandler()
registerResizeHandler()
deregisterResizeHandler()
getViewportScrollY()
getTotalActionItems()
Karena React memiliki peristiwa sintetis serta berbagai praktik dan pola coding terbaik, metode Adapter perlu diterapkan kembali.
Metode Pengambil Adaptor
Di file TopAppBar.js
, tambahkan metode JavaScript berikut ke TopAppBar
:
get adapter() {
const {actionItems} = this.props;
return {
hasClass: (className) => this.classes.split(' ').includes(className),
addClass: (className) => this.setState({classList: this.state.classList.add(className)}),
removeClass: (className) => {
const {classList} = this.state;
classList.delete(className);
this.setState({classList});
},
setStyle: this.setStyle,
getTopAppBarHeight: () => this.topAppBarElement.current.clientHeight,
registerScrollHandler: (handler) => window.addEventListener('scroll', handler),
deregisterScrollHandler: (handler) => window.removeEventListener('scroll', handler),
registerResizeHandler: (handler) => window.addEventListener('resize', handler),
deregisterResizeHandler: (handler) => window.removeEventListener('resize', handler),
getViewportScrollY: () => window.pageYOffset,
getTotalActionItems: () => actionItems && actionItems.length,
};
}
API adaptor untuk pendaftaran peristiwa scroll dan ubah ukuran diterapkan secara identik dengan versi JS non-framework, karena React tidak memiliki peristiwa sintetis untuk men-scroll atau mengubah ukuran dan tunduk pada sistem peristiwa DOM native. getViewPortScrollY
juga harus tunduk pada DOM native karena merupakan fungsi di objek window
, yang tidak ada di API React. Implementasi adaptor akan berbeda untuk setiap framework.
Anda mungkin melihat this.setStyle
tidak ada, yang dipanggil oleh metode get adapter
. Di file TopAppBar.js
, tambahkan metode JavaScript yang tidak ada ke class TopAppBar
:
setStyle = (varName, value) => {
const updatedStyle = Object.assign({}, this.state.style);
updatedStyle[varName] = value;
this.setState({style: updatedStyle});
}
Anda baru saja mengimplementasikan Adaptor. Perhatikan bahwa Anda mungkin melihat error di konsol pada tahap ini karena implementasi penuh belum selesai. Bagian berikutnya akan memandu Anda terkait cara menambahkan dan menghapus class CSS.
5. Mengimplementasikan metode Komponen
Mengelola Varian dan Class
React tidak memiliki API untuk mengelola class. Untuk meniru metode class tambahkan/hapus pada JavaScript native, tambahkan variabel status classList
. Ada tiga bagian kode di TopAppBar
yang berinteraksi dengan class CSS:
- Komponen
<TopAppBar />
melalui properticlassName
. - Metode Adapter melalui
addClass
atauremoveClass
. - Hard code dalam Komponen React
<TopAppBar />
.
Pertama, tambahkan impor berikut di bagian atas TopAppBar.js
, di bawah impor yang ada:
import classnames from 'classnames';
Lalu, tambahkan kode berikut di dalam deklarasi class Komponen TopAppBar
:
export default class TopAppBar extends React.Component {
constructor(props) {
super(props);
this.topAppBarElement = React.createRef();
}
state = {
classList: new Set(),
style: {},
};
get classes() {
const {classList} = this.state;
const {
alwaysCollapsed,
className,
short,
fixed,
prominent,
} = this.props;
return classnames('mdc-top-app-bar', Array.from(classList), className, {
'mdc-top-app-bar--fixed': fixed,
'mdc-top-app-bar--short': short,
'mdc-top-app-bar--short-collapsed': alwaysCollapsed,
'mdc-top-app-bar--prominent': prominent,
});
}
...
}
Jika Anda membuka http://localhost:8080, kotak centang Kontrol sekarang akan mengaktifkan/menonaktifkan nama class dari DOM.
Kode ini membuat TopAppBar
dapat digunakan oleh banyak developer. Developer dapat berinteraksi dengan TopAppBar
API, tanpa perlu mengkhawatirkan detail implementasi class CSS.
Anda telah berhasil menerapkan Adaptor. Bagian berikutnya akan memandu Anda membuat instance Fondasi.
Memasang dan Melepas Komponen
Pembuatan instance fondasi terjadi dalam metode componentDidMount
.
Pertama, impor fondasi Panel Aplikasi Atas MDC dengan menambahkan impor berikut setelah impor yang ada di TopAppBar.js
:
import {MDCTopAppBarFoundation, MDCFixedTopAppBarFoundation, MDCShortTopAppBarFoundation} from '@material/top-app-bar';
Selanjutnya, tambahkan kode JavaScript berikut ke dalam class TopAppBar
:
export default class TopAppBar extends React.Component {
...
foundation_ = null;
componentDidMount() {
this.initializeFoundation();
}
componentWillUnmount() {
this.foundation_.destroy();
}
initializeFoundation = () => {
if (this.props.short) {
this.foundation_ = new MDCShortTopAppBarFoundation(this.adapter);
} else if (this.props.fixed) {
this.foundation_ = new MDCFixedTopAppBarFoundation(this.adapter);
} else {
this.foundation_ = new MDCTopAppBarFoundation(this.adapter);
}
this.foundation_.init();
}
...
}
Salah satu praktik coding React yang baik adalah menentukan propTypes dan defaultProps. Tambahkan impor berikut setelah impor yang ada di TopAppBar.js:
import PropTypes from 'prop-types';
Kemudian, tambahkan kode berikut ke bagian bawah TopAppBar.js
(setelah class Komponen):
import PropTypes from 'prop-types';
TopAppBar.propTypes = {
alwaysCollapsed: PropTypes.bool,
short: PropTypes.bool,
fixed: PropTypes.bool,
prominent: PropTypes.bool,
title: PropTypes.string,
actionItems: PropTypes.arrayOf(PropTypes.element),
navIcon: PropTypes.element,
};
TopAppBar.defaultProps = {
alwaysCollapsed: false,
short: false,
fixed: false,
prominent: false,
title: '',
actionItems: null,
navIcon: null,
};
Anda kini telah berhasil menerapkan Komponen Reaksi Panel Aplikasi Teratas. Jika membuka http://localhost:8080, Anda dapat mencoba halaman demo. Halaman demo akan berfungsi sama seperti halaman demo MDC Web. Halaman demo akan terlihat seperti ini:
6. Rangkuman
Dalam tutorial ini, kita telah membahas cara menggabungkan Fondasi Web MDC untuk digunakan dalam aplikasi React. Ada beberapa library di GitHub dan npm yang menggabungkan Komponen Web MDC seperti yang dijelaskan dalam Mengintegrasikan ke Framework. Sebaiknya gunakan daftar yang ada di sini. Daftar ini juga menyertakan framework lain selain React seperti Angular dan Vue.
Tutorial ini menyoroti keputusan kami untuk membagi kode Web MDC menjadi 3 bagian, yaitu Foundation, Adapter, dan Komponen. Arsitektur ini memungkinkan komponen untuk berbagi kode umum saat bekerja dengan semua framework. Terima kasih telah mencoba React Komponen Material dan lihat library baru kami MDC React. Kami harap Anda menikmati codelab ini.