Skip to main content

lingxia_platform/
unsupported.rs

1#![allow(clippy::manual_async_fn)]
2
3use std::future::Future;
4use std::io::Read;
5use std::path::{Path, PathBuf};
6
7use crate::error::PlatformError;
8use crate::traits::app_runtime::{
9    AnimationType, AppRuntime, LxAppOpenMode, OpenUrlRequest, OpenUrlResult,
10};
11use crate::traits::device::{Device, DeviceHardware};
12use crate::traits::file::{
13    ChooseDirectoryRequest, ChooseFileRequest, FileDialogResult, FileService, OpenFileRequest,
14    RevealInFileManagerRequest,
15};
16use crate::traits::keyboard::AppKeyboard;
17use crate::traits::location::{Location, LocationRequestConfig};
18use crate::traits::media_interaction::{
19    ChooseMediaRequest, MediaInteraction, PreviewMediaRequest, SaveMediaRequest, ScanCodeRequest,
20};
21use crate::traits::media_runtime::{
22    CompressImageRequest, CompressVideoRequest, CompressedVideo, ExtractVideoThumbnailRequest,
23    ImageInfo, MediaRuntime, VideoInfo, VideoThumbnail,
24};
25use crate::traits::mouse::AppMouse;
26use crate::traits::network::Network;
27use crate::traits::pull_to_refresh::PullToRefresh;
28use crate::traits::screenshot::AppScreenshot;
29use crate::traits::secure_store::SecureStore;
30use crate::traits::share::{ShareRequest, ShareResult, ShareService};
31use crate::traits::stream_decoder::{VideoStreamDecoderHandle, VideoStreamDecoderManager};
32use crate::traits::ui::{ModalOptions, SurfacePresenter, ToastOptions, UIUpdate, UserFeedback};
33use crate::traits::update::UpdateService;
34use crate::traits::video_player::{VideoPlayerHandle, VideoPlayerManager};
35use crate::traits::wifi::Wifi;
36use crate::{AssetFileEntry, DeviceInfo, ScreenInfo};
37
38#[derive(Debug, Clone)]
39pub struct Platform {
40    data_dir: PathBuf,
41    cache_dir: PathBuf,
42    locale: String,
43}
44
45impl Default for Platform {
46    fn default() -> Self {
47        let base = std::env::temp_dir().join("lingxia");
48        Self {
49            data_dir: base.join("data"),
50            cache_dir: base.join("cache"),
51            locale: "en-US".to_string(),
52        }
53    }
54}
55
56impl Platform {
57    pub fn new(
58        data_dir: impl Into<PathBuf>,
59        cache_dir: impl Into<PathBuf>,
60        locale: impl Into<String>,
61    ) -> Result<Self, PlatformError> {
62        Ok(Self {
63            data_dir: data_dir.into(),
64            cache_dir: cache_dir.into(),
65            locale: locale.into(),
66        })
67    }
68}
69
70fn not_supported<T>(name: &str) -> Result<T, PlatformError> {
71    Err(PlatformError::NotSupported(format!(
72        "{name} is not supported on this platform"
73    )))
74}
75
76impl Device for Platform {
77    fn device_info(&self) -> DeviceInfo {
78        DeviceInfo {
79            brand: "unsupported".to_string(),
80            model: std::env::consts::OS.to_string(),
81            market_name: std::env::consts::OS.to_string(),
82            os_name: std::env::consts::OS.to_string(),
83            os_version: String::new(),
84        }
85    }
86
87    fn screen_info(&self) -> ScreenInfo {
88        ScreenInfo {
89            width: 0.0,
90            height: 0.0,
91            scale: 1.0,
92        }
93    }
94
95    fn vibrate(&self, _long: bool) -> Result<(), PlatformError> {
96        not_supported("vibrate")
97    }
98
99    fn make_phone_call(&self, _phone_number: &str) -> Result<(), PlatformError> {
100        not_supported("make_phone_call")
101    }
102}
103
104impl DeviceHardware for Platform {}
105impl SecureStore for Platform {}
106impl Network for Platform {}
107impl SurfacePresenter for Platform {}
108impl UpdateService for Platform {}
109impl Wifi for Platform {}
110impl AppScreenshot for Platform {}
111impl AppMouse for Platform {}
112impl AppKeyboard for Platform {}
113
114impl FileService for Platform {
115    fn review_file(
116        &self,
117        _request: OpenFileRequest,
118    ) -> impl Future<Output = Result<(), PlatformError>> + Send {
119        async { not_supported("review_file") }
120    }
121
122    fn open_external(
123        &self,
124        _request: OpenFileRequest,
125    ) -> impl Future<Output = Result<(), PlatformError>> + Send {
126        async { not_supported("open_external") }
127    }
128
129    fn reveal_in_file_manager(
130        &self,
131        _request: RevealInFileManagerRequest,
132    ) -> impl Future<Output = Result<(), PlatformError>> + Send {
133        async { not_supported("reveal_in_file_manager") }
134    }
135
136    fn choose_file(
137        &self,
138        _request: ChooseFileRequest,
139    ) -> impl Future<Output = Result<FileDialogResult, PlatformError>> + Send {
140        async { not_supported("choose_file") }
141    }
142
143    fn choose_directory(
144        &self,
145        _request: ChooseDirectoryRequest,
146    ) -> impl Future<Output = Result<FileDialogResult, PlatformError>> + Send {
147        async { not_supported("choose_directory") }
148    }
149}
150
151impl Location for Platform {
152    fn is_location_enabled(&self) -> Result<bool, PlatformError> {
153        not_supported("is_location_enabled")
154    }
155
156    fn request_location(
157        &self,
158        _config: LocationRequestConfig,
159    ) -> impl Future<Output = Result<String, PlatformError>> + Send {
160        async { not_supported("request_location") }
161    }
162}
163
164impl MediaInteraction for Platform {
165    fn preview_media(&self, _request: PreviewMediaRequest) -> Result<(), PlatformError> {
166        not_supported("preview_media")
167    }
168
169    fn cancel_preview(&self, _callback_id: u64) -> Result<(), PlatformError> {
170        not_supported("cancel_preview")
171    }
172
173    fn choose_media(
174        &self,
175        _request: ChooseMediaRequest,
176    ) -> impl Future<Output = Result<String, PlatformError>> + Send {
177        async { not_supported("choose_media") }
178    }
179
180    fn scan_code(
181        &self,
182        _request: ScanCodeRequest,
183    ) -> impl Future<Output = Result<String, PlatformError>> + Send {
184        async { not_supported("scan_code") }
185    }
186
187    fn save_image_to_photos_album(
188        &self,
189        _request: SaveMediaRequest,
190    ) -> impl Future<Output = Result<(), PlatformError>> + Send {
191        async { not_supported("save_image_to_photos_album") }
192    }
193
194    fn save_video_to_photos_album(
195        &self,
196        _request: SaveMediaRequest,
197    ) -> impl Future<Output = Result<(), PlatformError>> + Send {
198        async { not_supported("save_video_to_photos_album") }
199    }
200}
201
202impl MediaRuntime for Platform {
203    fn copy_album_media_to_file(
204        &self,
205        _uri: &str,
206        _dest_path: &Path,
207        _kind: crate::traits::media_interaction::MediaKind,
208    ) -> Result<(), PlatformError> {
209        not_supported("copy_album_media_to_file")
210    }
211
212    fn get_image_info(&self, _uri: &str) -> Result<ImageInfo, PlatformError> {
213        not_supported("get_image_info")
214    }
215
216    fn compress_image(&self, _request: &CompressImageRequest) -> Result<PathBuf, PlatformError> {
217        not_supported("compress_image")
218    }
219
220    fn compress_video(&self, _request: &CompressVideoRequest) -> Result<(), PlatformError> {
221        not_supported("compress_video")
222    }
223
224    fn cancel_compress_video(&self, _callback_id: u64) -> Result<(), PlatformError> {
225        not_supported("cancel_compress_video")
226    }
227
228    fn get_video_info(&self, _uri: &str) -> Result<VideoInfo, PlatformError> {
229        not_supported("get_video_info")
230    }
231
232    fn extract_video_thumbnail(
233        &self,
234        _request: &ExtractVideoThumbnailRequest,
235    ) -> Result<VideoThumbnail, PlatformError> {
236        not_supported("extract_video_thumbnail")
237    }
238}
239
240impl ShareService for Platform {
241    fn share(
242        &self,
243        _request: ShareRequest,
244    ) -> impl Future<Output = Result<ShareResult, PlatformError>> + Send {
245        async { not_supported("share") }
246    }
247}
248
249impl UIUpdate for Platform {
250    fn update_navbar_ui(&self, _appid: String) -> Result<(), PlatformError> {
251        not_supported("update_navbar_ui")
252    }
253
254    fn update_tabbar_ui(&self, _appid: String) -> Result<(), PlatformError> {
255        not_supported("update_tabbar_ui")
256    }
257}
258
259impl UserFeedback for Platform {
260    fn show_toast(&self, _options: ToastOptions) -> Result<(), PlatformError> {
261        not_supported("show_toast")
262    }
263
264    fn hide_toast(&self) -> Result<(), PlatformError> {
265        not_supported("hide_toast")
266    }
267
268    fn show_modal(
269        &self,
270        _options: ModalOptions,
271    ) -> impl Future<Output = Result<String, PlatformError>> + Send {
272        async { not_supported("show_modal") }
273    }
274
275    fn show_action_sheet(
276        &self,
277        _options: Vec<String>,
278        _cancel_text: String,
279        _item_color: String,
280    ) -> impl Future<Output = Result<String, PlatformError>> + Send {
281        async { not_supported("show_action_sheet") }
282    }
283}
284
285impl PullToRefresh for Platform {
286    fn start_pull_down_refresh(&self, _app_id: &str, _path: &str) -> Result<(), PlatformError> {
287        not_supported("start_pull_down_refresh")
288    }
289
290    fn stop_pull_down_refresh(&self, _app_id: &str, _path: &str) -> Result<(), PlatformError> {
291        not_supported("stop_pull_down_refresh")
292    }
293}
294
295impl VideoPlayerManager for Platform {
296    fn bind_player(
297        &self,
298        _component_id: &str,
299    ) -> Result<Box<dyn VideoPlayerHandle>, PlatformError> {
300        not_supported("bind_player")
301    }
302}
303
304impl VideoStreamDecoderManager for Platform {
305    fn create_stream_decoder(
306        &self,
307        _component_id: &str,
308    ) -> Result<Box<dyn VideoStreamDecoderHandle>, PlatformError> {
309        not_supported("create_stream_decoder")
310    }
311}
312
313impl AppRuntime for Platform {
314    fn read_asset<'a>(&'a self, _path: &str) -> Result<Box<dyn Read + 'a>, PlatformError> {
315        not_supported("read_asset")
316    }
317
318    fn asset_dir_iter<'a>(
319        &'a self,
320        _asset_dir: &str,
321    ) -> Box<dyn Iterator<Item = Result<AssetFileEntry<'a>, PlatformError>> + 'a> {
322        Box::new(std::iter::once(not_supported("asset_dir_iter")))
323    }
324
325    fn app_data_dir(&self) -> PathBuf {
326        self.data_dir.clone()
327    }
328
329    fn app_cache_dir(&self) -> PathBuf {
330        self.cache_dir.clone()
331    }
332
333    fn get_app_identifier(&self) -> Result<String, PlatformError> {
334        not_supported("get_app_identifier")
335    }
336
337    fn get_system_locale(&self) -> &str {
338        &self.locale
339    }
340
341    fn show_lxapp(
342        &self,
343        _appid: String,
344        _title: String,
345        _path: String,
346        _webtag: String,
347        _session_id: u64,
348        _open_mode: LxAppOpenMode,
349        _panel_id: String,
350    ) -> Result<(), PlatformError> {
351        not_supported("show_lxapp")
352    }
353
354    fn hide_lxapp(&self, _appid: String, _session_id: u64) -> Result<(), PlatformError> {
355        not_supported("hide_lxapp")
356    }
357
358    fn exit(&self) -> Result<(), PlatformError> {
359        not_supported("exit")
360    }
361
362    fn navigate(
363        &self,
364        _appid: String,
365        _path: String,
366        _webtag: String,
367        _animation_type: AnimationType,
368    ) -> Result<(), PlatformError> {
369        not_supported("navigate")
370    }
371
372    fn open_url(&self, _req: OpenUrlRequest) -> Result<OpenUrlResult, PlatformError> {
373        not_supported("open_url")
374    }
375}