use crate::core::{EditorDocument, Result};
use super::context::{EditorContext, ExtensionContext};
use super::manager::{ExtensionManager, ExtensionManagerInner};
#[cfg(feature = "std")]
use super::extension::{MessageHandler, StdMessageHandler};
#[cfg(feature = "std")]
use super::manager::EventSender;
#[cfg(not(feature = "std"))]
use super::extension::NoOpMessageHandler;
#[cfg(feature = "std")]
use std::collections::HashMap;
#[cfg(not(feature = "std"))]
use alloc::collections::BTreeMap as HashMap;
#[cfg(not(feature = "std"))]
use alloc::{boxed::Box, string::String};
#[cfg(feature = "std")]
use std::sync::mpsc;
#[cfg(feature = "multi-thread")]
use std::sync::Arc;
#[cfg(feature = "multi-thread")]
use parking_lot::Mutex;
#[cfg(not(feature = "multi-thread"))]
use core::cell::RefCell;
#[cfg(all(not(feature = "multi-thread"), not(feature = "std")))]
use alloc::rc::Rc;
#[cfg(all(not(feature = "multi-thread"), feature = "std"))]
use std::rc::Rc;
impl ExtensionManagerInner {
fn new() -> Self {
#[cfg(feature = "std")]
let (tx, _rx) = mpsc::channel();
Self {
extensions: HashMap::new(),
extension_states: HashMap::new(),
commands: HashMap::new(),
config: HashMap::new(),
extension_data: HashMap::new(),
#[cfg(feature = "std")]
event_tx: tx,
#[cfg(feature = "std")]
message_handler: Box::new(StdMessageHandler),
#[cfg(not(feature = "std"))]
message_handler: Box::new(NoOpMessageHandler),
}
}
}
impl ExtensionManager {
pub fn new() -> Self {
#[cfg(feature = "multi-thread")]
{
Self {
inner: Arc::new(Mutex::new(ExtensionManagerInner::new())),
}
}
#[cfg(not(feature = "multi-thread"))]
{
Self {
inner: RefCell::new(ExtensionManagerInner::new()),
}
}
}
#[cfg(feature = "std")]
pub fn with_event_channel(
event_tx: EventSender,
message_handler: Box<dyn MessageHandler>,
) -> Self {
let inner = ExtensionManagerInner {
extensions: HashMap::new(),
extension_states: HashMap::new(),
commands: HashMap::new(),
config: HashMap::new(),
extension_data: HashMap::new(),
event_tx,
message_handler,
};
#[cfg(feature = "multi-thread")]
{
Self {
inner: Arc::new(Mutex::new(inner)),
}
}
#[cfg(not(feature = "multi-thread"))]
{
Self {
inner: RefCell::new(inner),
}
}
}
pub fn create_context<'a>(
&'a mut self,
extension_name: String,
document: Option<&'a mut EditorDocument>,
) -> Result<Box<dyn ExtensionContext + 'a>> {
#[cfg(feature = "multi-thread")]
{
Ok(Box::new(EditorContext {
document,
manager: self.clone(),
extension_name,
}))
}
#[cfg(not(feature = "multi-thread"))]
{
let config_clone = self.inner.borrow().config.clone();
let shared_config = Rc::new(RefCell::new(config_clone));
Ok(Box::new(EditorContext {
document,
manager: self,
manager_mut_state: shared_config,
extension_name,
}))
}
}
}