diff --git a/ChatOptions.hs b/ChatOptions.hs index c95ddea85f..72bc6f9854 100644 --- a/ChatOptions.hs +++ b/ChatOptions.hs @@ -7,6 +7,7 @@ import qualified Data.ByteString.Char8 as B import Options.Applicative import Simplex.Messaging.Agent.Transmission (SMPServer (..), smpServerP) import System.FilePath (combine) +import System.Info (os) import Types data ChatOpts = ChatOpts @@ -17,8 +18,7 @@ data ChatOpts = ChatOpts } chatOpts :: FilePath -> Parser ChatOpts -chatOpts appDir = do - let defaultDbFilePath = combine appDir "smp-chat.db" +chatOpts appDir = ChatOpts <$> option (Just <$> str) @@ -32,7 +32,7 @@ chatOpts appDir = do ( long "database" <> short 'd' <> metavar "DB_FILE" - <> help ("sqlite database file path (" ++ defaultDbFilePath ++ ")") + <> help ("sqlite database file path (" <> defaultDbFilePath <> ")") <> value defaultDbFilePath ) <*> option @@ -48,9 +48,14 @@ chatOpts appDir = do ( long "term" <> short 't' <> metavar "TERM" - <> help "terminal mode: \"editor\", \"simple\" or \"basic\" (editor)" - <> value TermModeEditor + <> help ("terminal mode: editor, simple or basic (" <> termModeName deafultTermMode <> ")") + <> value deafultTermMode ) + where + defaultDbFilePath = combine appDir "smp-chat.db" + deafultTermMode + | os == "mingw32" = TermModeBasic + | otherwise = TermModeEditor parseSMPServer :: ReadM SMPServer parseSMPServer = eitherReader $ A.parseOnly (smpServerP <* A.endOfInput) . B.pack diff --git a/ChatTerminal.hs b/ChatTerminal.hs index 78a167982d..641daf55bf 100644 --- a/ChatTerminal.hs +++ b/ChatTerminal.hs @@ -3,9 +3,9 @@ {-# LANGUAGE NamedFieldPuns #-} {-# LANGUAGE OverloadedStrings #-} -#ifdef mingw32_HOST_OS -{-# LANGUAGE ForeignFunctionInterface #-} -#endif +-- #ifdef mingw32_HOST_OS +-- {-# LANGUAGE ForeignFunctionInterface #-} +-- #endif module ChatTerminal ( ChatTerminal (..), @@ -33,10 +33,10 @@ import qualified System.Console.ANSI as C import System.IO import Types -#ifdef mingw32_HOST_OS -import Data.Char -import Foreign.C.Types -#endif +-- #ifdef mingw32_HOST_OS +-- import Data.Char +-- import Foreign.C.Types +-- #endif data ChatTerminal = ChatTerminal { inputQ :: TBQueue ByteString, @@ -336,13 +336,13 @@ getChatLn ct = do (s <>) <$> getLn stdin getHiddenChar :: IO Char -#ifdef mingw32_HOST_OS -getHiddenChar = fmap (chr.fromEnum) c_getch -foreign import ccall unsafe "conio.h getch" - c_getch :: IO CInt -#else +-- #ifdef mingw32_HOST_OS +-- getHiddenChar = fmap (chr.fromEnum) c_getch +-- foreign import ccall unsafe "conio.h getch" +-- c_getch :: IO CInt +-- #else getHiddenChar = getChar -#endif +-- #endif setTTY :: BufferMode -> IO () setTTY mode = do diff --git a/Main.hs b/Main.hs index 4c1f87abb4..ac33b81e50 100644 --- a/Main.hs +++ b/Main.hs @@ -28,6 +28,8 @@ import Simplex.Messaging.Agent.Transmission import Simplex.Messaging.Client (smpDefaultConfig) import Simplex.Messaging.Util (bshow, raceAny_) import System.Directory (getAppUserDataDirectory) +import System.Exit (exitFailure) +import System.Info (os) import Types cfg :: AgentConfig @@ -117,11 +119,7 @@ chatHelpInfo = main :: IO () main = do - appDir <- getAppUserDataDirectory "simplex" - ChatOpts {dbFileName, smpServer, name, termMode} <- getChatOpts appDir - putStrLn "simpleX chat prototype" - putStrLn $ "db: " ++ dbFileName - putStrLn "type \"/help\" for usage information" + ChatOpts {dbFileName, smpServer, name, termMode} <- welcomeGetOpts let user = Contact <$> name t <- getChatClient smpServer user ct <- newChatTerminal (tbqSize cfg) user termMode @@ -130,6 +128,25 @@ main = do env <- newSMPAgentEnv cfg {dbFile = dbFileName} dogFoodChat t ct env +welcomeGetOpts :: IO ChatOpts +welcomeGetOpts = do + appDir <- getAppUserDataDirectory "simplex" + opts@ChatOpts {dbFileName, termMode} <- getChatOpts appDir + putStrLn "simpleX chat prototype" + putStrLn $ "db: " <> dbFileName + when (os == "mingw32") $ windowsWarning termMode + putStrLn "type \"/help\" for usage information" + pure opts + +windowsWarning :: TermMode -> IO () +windowsWarning = \case + m@TermModeBasic -> do + putStrLn $ "running in Windows (terminal mode is " <> termModeName m <> ", no utf8 support)" + putStrLn "it is recommended to use Windows Subsystem for Linux (WSL)" + m -> do + putStrLn $ "running in Windows, terminal mode " <> termModeName m <> " is not supported" + exitFailure + dogFoodChat :: ChatClient -> ChatTerminal -> Env -> IO () dogFoodChat t ct env = do c <- runReaderT getSMPAgentClient env diff --git a/Types.hs b/Types.hs index 8f0a3c945b..2b5c9b6d6e 100644 --- a/Types.hs +++ b/Types.hs @@ -1,3 +1,5 @@ +{-# LANGUAGE LambdaCase #-} + module Types where import Data.ByteString.Char8 (ByteString) @@ -5,3 +7,9 @@ import Data.ByteString.Char8 (ByteString) newtype Contact = Contact {toBs :: ByteString} data TermMode = TermModeBasic | TermModeSimple | TermModeEditor deriving (Eq) + +termModeName :: TermMode -> String +termModeName = \case + TermModeBasic -> "basic" + TermModeSimple -> "simple" + TermModeEditor -> "editor"