Kami membuat aplikasi desktop asli lintas platform di Angular

angular-nodegui


Seperti yang mungkin sudah Anda ketahui, Angular sudah ada di banyak platform:



Yah, tentu saja, tidak ada cukup desktop di sini (jangan bicara tentang Electron).


Untuk membuat aplikasi desktop, ada banyak solusi menggunakan templat, misalnya, solusi seperti JavaFx, Qt, WPF. Semuanya, kecuali yang terakhir, adalah cross-platform.


Tetapi bagaimana jika kita ingin menggunakan kerangka kerja yang sudah dikenal dan membuat aplikasi asli di atasnya? Sebenarnya, itulah yang saya lakukan.


Untuk memulainya, saya melihat apa yang saat ini tersedia, dan apa yang mungkin telah dilakukan di bawah Angular.


Sebenarnya, dengan cara ini saya ingin menunjukkan bahwa Anda dapat melakukan apa saja pada Angular, dan saya telah melakukan segala macam hal selama beberapa tahun berturut-turut.

Cari


libui-node


Ini adalah pustaka GUI yang ringan dan portabel yang memanfaatkan fitur asli GUI untuk setiap platform yang didukungnya. Itu datang sebagai alternatif untuk Elektron.


Contoh aplikasi sederhana:


const win = new libui.UiWindow('Test window', 800, 600, false); 

Di bawah tenda, ia memiliki pengikat libui sederhana. (Libui: perpustakaan GUI portabel untuk C). Semua ini dilakukan melalui node-gyp, sebuah utilitas yang dirancang untuk mengkompilasi ekstensi asli untuk Node.js. libui-node mencakup lebih dari 30 komponen yang sudah jadi, yah, dan jika Anda tiba-tiba memutuskan untuk membuat sesuatu yang kustom, Anda perlu menyelami kode dalam C. Dan selain itu, komponen itu sendiri ditulis 2 tahun yang lalu, dan sejak itu diperbarui. Mungkin semuanya begitu baik sehingga tidak perlu melakukan perubahan, dan 30 komponen ini cukup untuk pengembangan, baik, atau tidak ada yang membutuhkan proyek sama sekali.


Sebenarnya, aplikasi yang sudah selesai mungkin terlihat seperti ini:


libui-node libui-node


Pribumi proton dan Vuido


Dan ini dia sedikit lebih menarik, asli proton dan vuido adalah libui-node yang sama, hanya di bawah React and Vue. Pembungkus yang sesuai ditulis di bawah komponen libui-node. Meskipun jumlah bintang di github (9k dan 6k), proyek-proyek tersebut ditinggalkan, dan hampir tidak ada yang menggunakannya. Dari semua yang saya dapat temukan, ini adalah aplikasi yang sangat sederhana. Masalah lain yang saya temukan adalah masalah dengan kustomisasi UI itu sendiri, tidak mungkin untuk melakukannya dalam libui, dan penulis proyek sedang mempertimbangkan untuk menulis ulang semuanya di Qt.


Libui sendiri cukup populer untuk menulis semua jenis binding, penggemar bahkan menyeretnya dalam php

Aplikasi yang sudah selesai mungkin terlihat seperti ini:


Asli proton Asli proton


Antarmuka yang agak membosankan tanpa penyesuaian, sehingga opsi ini segera menghilang.


Atau mungkin menggunakan Qt?


Qt, js, css


Tentu saja Anda mendengar tentang Qt, dan fakta bahwa itu dapat ditemukan di mana-mana, tetapi tidak banyak yang mendengar bahwa itu sekarang terintegrasi dengan Javascript di luar kotak. QML memungkinkan konstruksi deklaratif antarmuka pengguna menggunakan binder properti dan, dengan demikian, memperluas kemampuan elemen QML yang ada. Tentu saja, ini adalah Javascript yang lebih ketat daripada di web. Anda dapat menulis sesuatu yang mirip dengan ES5 menggunakan objek QML, tetapi Anda tidak akan memiliki DOM API.


Hanya catatan singkat, bagaimana Anda menulis dalam Qt di bawah C ++:


 #include <QApplication> #include <QPushButton> int main(int argc, char *argv[]) { QApplication app(argc, argv); *// Important * QPushButton hello("Hello world!"); hello.resize(100, 30); hello.show(); return app.exec(); *// Important *} 

Seperti apa kode Anda dalam Qml:


 Item { function factorial(a) { a = parseInt(a); if (a <= 0) return 1; else return a * factorial(a - 1); } MouseArea { anchors.fill: parent onClicked: console.log(factorial(10)) } } 

Komponen-komponen ini dapat dibuat secara dinamis.


QML juga memiliki sistem tipe besar, yang pasti akan berguna ketika mendefinisikan semua ini dalam naskah.


Anda juga dapat dengan mudah menyesuaikan komponen:


 Reactangle { id: redRectId width: 50 color: red } 

Hampir seperti CSS, bukan?


Yang masih harus ditambahkan adalah apa yang dapat dilakukan Qt pada kebanyakan platform.


Dan kita akan memiliki Node.js


Saat mencari "nodejs + qt", kami akan segera mendapatkan node-qt , tetapi segera menarik perhatian bahwa produk telah lama mati, dan terakhir kali menunjukkan tanda-tanda kehidupan 8 tahun yang lalu.


Namun demikian, dalam pencarian Anda dapat menemukan proyek yang sangat baru - NodeGui.


NodeGui


Seperti banyak perpustakaan untuk Gui, Qt menggunakan loop acara / pesannya untuk memproses acara dari widget. Oleh karena itu, ketika kami memanggil app.exec (), Qt memulai loop pesan dan memblokirnya di sana. Semua ini baik ketika hanya ada satu loop pesan di seluruh aplikasi. Tetapi karena kita perlu menggunakan Qt dengan NodeJs, dan yang terakhir juga memiliki loop acara sendiri, tidak mungkin untuk mengintegrasikannya dengan mudah. Tetapi keputusan seperti itu telah dibuat, misalnya, bundel yang sama dengan Electron atau yode. Solusi ini memiliki kekhasan sendiri, mereka meningkatkan setidaknya 2 proses - untuk utas utama, dan untuk penyaji. Meskipun demikian, pendekatan ini memiliki keuntungan yang signifikan, tidak perlu memodifikasi NodeJs atau Chromium.


Dalam kasus NodeGui, situasinya sedikit berbeda, ada satu proses untuk semuanya, dan dengan demikian, tidak perlu meleset peristiwa antara proses. Nodejs bercabang dua untuk ini - dan perbaikan kecil dilakukan untuk pengikat yang diperlukan di Qt. Dan sekarang Anda perlu memulai proses tidak seperti mainnj mainnode, tetapi qode main.js. Untungnya, qode diterbitkan sebagai modul npm di paket @ nodegui / qode. Untuk memulai dunia halo sederhana, Anda perlu menginstal beberapa paket lagi, untuk detail lebih lanjut untuk setiap OS yang dapat Anda lihat di situs web resmi: https://docs.nodegui.org/docs/guides/getting-started


Secara default, di nodegui, semuanya adalah widget, dan mereka dapat dipasangi berbagai templat. Saat ini ada 2 jenis template di nodegui: FlexLayout dan QGridLayout.


Gaya dalam Nodegui


Saat ini, Anda dapat mengatur gaya untuk widget baik inline maupun melalui styleSheet.


 widget.setInlineStyle(`color: green`) view.setStyleSheet(` `#helloLabel { color: red; padding: 10px; } #worldLabel { color: green; padding: 10px; } #rootView { background-color: black; } `); 

Qt secara default mendukung semua penyeleksi CSS2 ( https://doc.qt.io/qt-5/stylesheet-syntax.html#selector-types )


Itu juga tidak dilakukan tanpa properti khusus untuk komponen penataan gaya. Untungnya, properti seperti itu sudah dijelaskan di dok Qt dan dikunyah di stackoverflow.


 *QPushButton* { qproperty-iconsize: 20px 20px; } 

Sudut


Penulis proyek telah menerapkan dukungan untuk bereaksi, tetapi tentu saja, semua orang lupa tentang keberadaan Angular.

Seperti yang sudah ditulis di awal, Angular dapat melakukan sebagian besar platform, tetapi sejauh ini belum ada platform untuk desktop. Karena API Angular yang dirancang dengan baik dan terstruktur, implementasi nodegui di bawah Angular bermula untuk menulis platformBrowserDynamic kustom dengan Renderer dan menggantinya dalam aplikasi.


Tapi bagaimana cara kerjanya dari dalam ke luar?


Kami memiliki main.ts bersyarat, dan kami akan mulai dengan itu.


Proses boot terdiri dari dua bagian: membuat platform dan melemparkan modul awal ke dalamnya.


 platformBrowserDynamic().bootstrapModule(AppModule); 

Melalui createPlatformFactory, kami dapat membuat benar-benar semua platform yang Anda butuhkan. Bagi kami, ini berarti bahwa kami tidak ingin bekerja dengan DOM yang biasa, dan sebagai tambahan kami akan membahas deskripsi skema interaksi elemen ketika bekerja dengan render. Informasi lebih lanjut tentang membuat platform dapat ditemukan di sumber.


Pada modul awal, kami menjelaskan komponen mana yang akan di-render terlebih dahulu. Saat membuat instance komponen, Angular memanggil renderComponent dan, mengaitkannya dengan render yang diinginkan yang diterimanya, dengan instance komponen itu. Segala sesuatu yang akan dilakukan Angular mengenai rendering komponen (membuat elemen, mengatur atribut, berlangganan acara, dll.) Akan melalui renderer ini. Oleh karena itu, kita perlu mengganti RendererFactory.


Pertama-tama, di Renderer kami akan tertarik dengan metode createElement. Dalam metode ini, kita mendapatkan nama tag, dan dari sana kita perlu membuat komponen yang diinginkan. Untungnya, nodegui memiliki satu set komponen dasar, yang saya teliti dengan hati-hati dan menjelaskan bagaimana mereka akan dirender dalam kerangka Angular, melemparkan semuanya ke direktori komponen umum. Tindakan lain dengan komponen standar juga akan melewati penyaji ini. Lebih detail .


[https://blog.nrwl.io/†(https://blog.nrwl.io/) https://blog.nrwl.io/


Untuk mendengarkan acara di renderer, nama acara dilemparkan, dan untuk komponen ini kita menggantung eventListener yang biasa.


 listen(target: any, eventName: string, callback: (event: any) => boolean | void): () => void { const callbackFunc = (e: NativeEvent) => callback.call(target, e); target.addEventListener(eventName, callbackFunc); return () => target.removeEventListener(eventName, callbackFunc); } 

Peristiwa komponen persis sama dengan Qt, misalnya, alih-alih yang biasa (click)=”clickFunc($event)” Anda harus menulis (clicked) = ”clickFunc($event)” .


Saat ini 16 komponen standar tersedia. Tetapi jika Anda perlu menulis komponen khusus Anda, maka selalu ada peluang untuk melakukan ini melalui QWidget.


Router juga dibuat untuk membuat aplikasi kita serapat mungkin dengan Angular.


 const appRoutes: Routes = [ { path: 'home', component: HomeComponent }, { path: 'about', component: AboutComponent } ]; // AppModule imports ... NodeguiRouterModule.forRoot(appRoutes), 

Aplikasi nodegui sudut
Aplikasi nodegui sudut


aplikasi cuaca
aplikasi cuaca


Kami mengumpulkan dalam prod


Untuk membangun aplikasi yang sudah jadi, nodegui memiliki paket sendiri - @nodegui/packer.


Utilitasnya sangat sederhana, sejauh ini terdiri dari 2 tim.


npx nodegui-packer - init myapp


Perintah ini akan membuat folder pengemasan yang berisi templat. Anda dapat mengubah konten untuk menambahkan ikon, mengubah nama, deskripsi, dan informasi aplikasi lainnya, serta menambahkan dependensi yang diperlukan.


npx nodegui-packer - pack

Perintah ini meluncurkan alat yang diperlukan untuk pengemasan (misalnya, macdeployqt untuk mac) dan mengemas dependensi.


Kesimpulannya


Sebagai kesimpulan, saya ingin membandingkan hasilnya dengan solusi web lain di desktop (hasil peluncuran di bawah Mac OS).


ukuran unduhan ukuran unduhan


penggunaan memori penggunaan memori



Tautan ke proyek:
irustm / angular-nodegui
* Bangun aplikasi desktop berkinerja tinggi, asli dan lintas platform dengan Angular. NodeGUI Angular didukung oleh Angular


Informasi tentang proyek:
https://t.me/ngFanatic


Informasi tentang proyek open source saya
https://twitter.com/irustm

Source: https://habr.com/ru/post/id480396/


All Articles