@@ -10,18 +10,37 @@
10-- Each line of the input config is processed individually. Lines that fail to parse are ignored.
10-- Each line of the input config is processed individually. Lines that fail to parse are ignored.
11-- Later entries take precedence over earlier.
11-- Later entries take precedence over earlier.
13−-- = Classify Table Overrides
13+-- For all directives:
16+-- string := \"\\\"\" chars+ \"\\\"\"
26+-- \"debugLog\" string
29+-- The value of the environment variable @VTY_DEBUG_LOG@ is equivalent to a debugLog entry at the
30+-- end of the last config file.
32+-- = Input Table Directives
15-- == @map@
34-- == @map@
17-- Directive format:
36-- Directive format:
20−-- entry := \"map\" string key modifier_list
39+-- \"map\" string key modifier_list
21−-- key := KEsc | KChar Char | KBS ... (same as 'Key')
41+-- key := KEsc | KChar Char | KBS ... (same as 'Key')
22−-- modifier_list := \"[\" modifier+ \"]\"
42+-- modifier_list := \"[\" modifier+ \"]\"
23−-- modifier := MShift | MCtrl | MMeta | MAlt
43+-- modifier := MShift | MCtrl | MMeta | MAlt
24−-- string := \"\\\"\" chars+ \"\\\"\"
27-- EG: If the contents are
46-- EG: If the contents are
@@ -34,6 +53,12 @@
34-- Then the bytes @\"\\ESC[B\"@ will result in the KUp event. The bytes @\"\\ESC[1;3B\"@ will result
53-- Then the bytes @\"\\ESC[B\"@ will result in the KUp event. The bytes @\"\\ESC[1;3B\"@ will result
35-- in the event KDown with the MAlt modifier.
54-- in the event KDown with the MAlt modifier.
56+-- If a debug log is requested then vty will output the current input table to the log in the above
59+-- EG: Set VTY_DEBUG_LOG. Run vty. Check debug log for incorrect mappings. Add corrected mappings to
37module Graphics.Vty.Config where
62module Graphics.Vty.Config where
39-- ignore warning on GHC 7.6+. Required for GHC 7.4
64-- ignore warning on GHC 7.6+. Required for GHC 7.4
@@ -62,9 +87,10 @@ import qualified Text.Parsec.Token as P
63data Config = Config
88data Config = Config
64 { specifiedEscPeriod :: Maybe Int
89 { specifiedEscPeriod :: Maybe Int
65− -- | Debug information is appended to the file.
90+ -- | Debug information is appended to this file if not Nothing.
66 , debugLog :: Maybe FilePath
91 , debugLog :: Maybe FilePath
67− -- | The (input byte, output event) pairs override VTY\'s built-in tables as well as terminfo.
92+ -- | The (input byte, output event) pairs extend the internal input table of VTY and the table
69 -- See "Graphics.Vty.Config" module documentation for documentation of the @map@ directive.
95 -- See "Graphics.Vty.Config" module documentation for documentation of the @map@ directive.
70 , inputOverrides :: ClassifyTable
96 , inputOverrides :: ClassifyTable
@@ -97,10 +123,12 @@ type ConfigParser s a = ParsecT s () (Writer Config) a
97-- | Config from @'getAppUserDataDirectory'/config@ and @$VTY_CONFIG_FILE@
123-- | Config from @'getAppUserDataDirectory'/config@ and @$VTY_CONFIG_FILE@
98userConfig :: IO Config
124userConfig :: IO Config
99userConfig = do
125userConfig = do
100− vtyConfig <- (mappend <$> getAppUserDataDirectory "vty" <*> pure "/config") >>= parseConfigFile
126+ userConfig <- (mappend <$> getAppUserDataDirectory "vty" <*> pure "/config") >>= parseConfigFile
101 overridePath <- tryJust (guard . isDoesNotExistError) $ getEnv "VTY_CONFIG_FILE"
127 overridePath <- tryJust (guard . isDoesNotExistError) $ getEnv "VTY_CONFIG_FILE"
102 overrideConfig <- either (const $ return def) parseConfigFile overridePath
128 overrideConfig <- either (const $ return def) parseConfigFile overridePath
103− return $ vtyConfig `mappend` overrideConfig
129+ debugLogPath <- tryJust (guard . isDoesNotExistError) $ getEnv "VTY_DEBUG_LOG"
130+ let debugLogConfig = either (const $ return def) (def { debugLog = Just debugLogPath })
131+ return $ mconcat [userConfig, overrideConfig, debugLogConfig]
105parseConfigFile :: FilePath -> IO Config
133parseConfigFile :: FilePath -> IO Config
106parseConfigFile path = do
134parseConfigFile path = do
@@ -130,7 +158,7 @@ configLanguage = LanguageDef
130configLexer :: Stream s m Char => P.GenTokenParser s u m
158configLexer :: Stream s m Char => P.GenTokenParser s u m
131configLexer = P.makeTokenParser configLanguage
159configLexer = P.makeTokenParser configLanguage
133−parseOverride = do
161+mapDecl = do
134 void $ string "map"
162 void $ string "map"
135 P.whiteSpace configLexer
163 P.whiteSpace configLexer
136 bytes <- P.stringLiteral configLexer
164 bytes <- P.stringLiteral configLexer
@@ -181,9 +209,15 @@ parseModifier = do
181 "MAlt" -> return MAlt
209 "MAlt" -> return MAlt
182 _ -> fail $ m ++ " is not a valid modifier identifier"
210 _ -> fail $ m ++ " is not a valid modifier identifier"
213+ void $ string "debugLog"
214+ P.whiteSpace configLexer
215+ path <- P.stringLiteral configLexer
216+ lift $ tell $ def { debugLog = Just path }
184ignoreLine = void $ manyTill anyChar newline
218ignoreLine = void $ manyTill anyChar newline
186parseConfig = void $ many $ do
220parseConfig = void $ many $ do
187 P.whiteSpace configLexer
221 P.whiteSpace configLexer
188− let directives = [parseOverride]
222+ let directives = [mapDecl, debugLogDecl]
189 try (choice directives) <|> ignoreLine
223 try (choice directives) <|> ignoreLine