title: Python curses not accept curses.KEY_UP as input
body: <p>I need your help in understanding the mistake in my new menu based python program.</p>
  
  <p>I have created a menu based python using the curses library. The program works fine with main menu options by accepting all the keys including special keys as input when getting user input via <code>getch()</code> but with a sub-menu list it fails to accept the special key as input.</p>
  
  <pre><code>   # Increment or Decrement
          elif c == curses.KEY_DOWN: # down arrow
              if self.option &lt; len(self.submenu):
                  self.option += 1
              else: self.option = 0
          elif c == curses.KEY_UP: # up arrow
              if self.option &gt; 0:
                  self.option -= 1
              else: self.option = len(self.submenu)
  </code></pre>
  
  <p>So above the is condition I am using to select the option but no input is sent to curses when I am using the UP/DOWN arrow keys </p>
  
  <p>I am sharing my full code below</p>
  
  <pre><code>import curses, os, traceback, json
  
  
  file1 = json.loads(open('/etc/ansible/org/json/tag_definition.json').read())
  submenu = list(file1.keys())
  
  cfg_dict = {'InstanceName': 'NONE',
              'Environment': 'NONE',
              'InstanceType':'t2.micro',
              'SystemOwner':'1',
          'LifeCycle':'NONE',
          'DeptName':'NONE',
          'Org':'NONE'}
  
  
  
  class CursedMenu(object):
      '''A class which abstracts the horrors of building a curses-based menu system'''
      def __init__(self):
          '''Initialization'''
          self.screen = curses.initscr()
          curses.noecho()
          curses.cbreak()
          curses.start_color()
          self.screen.keypad(1)
  
          # Highlighted and Normal line definitions
          curses.init_pair(1, curses.COLOR_BLACK, curses.COLOR_WHITE)
          self.highlighted = curses.color_pair(1)
          self.normal = curses.A_NORMAL
  
  
      def show(self, options, title="Title", subtitle="Subtitle"):
          '''Draws a menu with the given parameters'''
          self.set_options(options)
          self.title = title.upper()
          self.subtitle = subtitle.upper()
          self.selected = 0
          self.draw_menu()
  
  
      def set_options(self, options):
          '''Validates that the last option is "Exit"'''
          if options[-1] is not 'Exit':
              options.append('Exit')
          self.options = options
  
      def set_submenu(self, submenu):
          '''Validates that the last option is "Exit"'''
          if submenu[-1] is not 'Exit':
              submenu.append('Exit')
          self.submenu = submenu
  
      def draw_dict(self):
          self.screen.addstr(8, 35, " "*43, curses.A_BOLD)
          self.screen.addstr(10, 35," "*43, curses.A_BOLD)
          self.screen.addstr(12, 35," "*43, curses.A_BOLD)
          self.screen.addstr(14, 35," "*43, curses.A_BOLD)
          self.screen.addstr(16, 35," "*43, curses.A_BOLD)
          self.screen.addstr(18, 35," "*43, curses.A_BOLD)
          self.screen.addstr(20, 35," "*43, curses.A_BOLD)
          self.screen.addstr(8, 35, cfg_dict['InstanceName'], curses.A_STANDOUT)
          self.screen.addstr(10, 35,cfg_dict['Environment'], curses.A_STANDOUT)
          self.screen.addstr(12, 35,cfg_dict['InstanceType'], curses.A_STANDOUT)
          self.screen.addstr(14, 35,cfg_dict['SystemOwner'], curses.A_STANDOUT)
          self.screen.addstr(16, 35,cfg_dict['LifeCycle'], curses.A_STANDOUT)
          self.screen.addstr(18, 35,cfg_dict['DeptName'], curses.A_STANDOUT)
          self.screen.addstr(20, 35,cfg_dict['Org'], curses.A_STANDOUT)
          self.screen.refresh()
  
      def draw_menu(self):
          '''Actually draws the menu and handles branching'''
          request = ""
          try:
              while request is not "Exit":
                  self.draw()
                  request = self.get_user_input()
                  self.handle_request(request)
              self.__exit__()
  
          # Also calls __exit__, but adds traceback after
          except Exception as exception:
              self.__exit__()
              traceback.print_exc()
  
  
      def draw(self):
          '''Draw the menu and lines'''
          #self.screen.border(0)
          self.screen.subwin(40, 80, 0, 0).box()
          self.screen.addstr(2,30, self.title, curses.A_STANDOUT|curses.A_BOLD) # Title for this menu
          self.screen.hline(3, 1, curses.ACS_HLINE, 78)
          self.screen.addstr(4,2, self.subtitle, curses.A_BOLD) #Subtitle for this menu
          # Display all the menu items, showing the 'pos' item highlighted
          left = 2
          for index in range(len(self.options)):
              menu_name = len(self.options[index])
              textstyle = self.normal
              if index == self.selected:
                  textstyle = self.highlighted
              self.screen.addstr(5, left, "%d.%s" % (index+1, self.options[index]), textstyle)
              left = left + menu_name + 3
          self.screen.addstr(8, 4, "                Instance Name:", curses.A_BOLD)
          self.screen.addstr(10, 4,"                  Environment:", curses.A_BOLD)
          self.screen.addstr(12, 4,"                Instance Type:", curses.A_BOLD)
          self.screen.addstr(14, 4,"                  SystemOwner:", curses.A_BOLD)
          self.screen.addstr(16, 4,"                    LifeCycle:", curses.A_BOLD)
          self.screen.addstr(18, 4,"              Department Name:", curses.A_BOLD)
          self.screen.addstr(20, 4,"                          Org:", curses.A_BOLD)
          self.draw_dict()
          self.screen.refresh()
  
      def get_user_input(self):
          '''Gets the user's input and acts appropriately'''
          user_in = self.screen.getch() # Gets user input
  
          '''Enter and Exit Keys are special cases'''
          if user_in == 10:
              return self.options[self.selected]
          if user_in == 27:
              return self.options[-1]
          if user_in == (curses.KEY_END, ord('!')):
              return self.options[-1]
  
          # This is a number; check to see if we can set it
          if user_in &gt;= ord('1') and user_in &lt;= ord(str(min(9,len(self.options)+1))):
              self.selected = user_in - ord('0') - 1 # convert keypress back to a number, then subtract 1 to get index
              return
  
          # Increment or Decrement
          if user_in == curses.KEY_LEFT: # left arrow
              self.selected -=1
          if user_in == curses.KEY_RIGHT: # right arrow
              self.selected +=1
          self.selected = self.selected % len(self.options)
          return
  
  
  
      def handle_request(self, request):
          '''This is where you do things with the request'''
          if request is "Org":
             self.org_func()
          if request is None: return
  
      def org_func(self):
          '''Actually draws the submenu and handles branching'''
          c = None
          self.option = 0
          self.set_submenu(submenu)
          height = len(self.submenu)
          while c != 10:
              self.s = curses.newwin(height+2, 20, 6, 14)
              self.s.box()
              for index in range(len(self.submenu)):
                  textstyle = self.normal
                  if index == self.option:
                      textstyle = self.highlighted
                  self.s.addstr(index+1,1, "%d-%s" % (index+1, self.submenu[index]), textstyle)
              self.s.refresh()
              c = self.s.getch() # Gets user input
              if c == ord('k'):
                  d = self.submenu[self.option]
                  cfg_dict['Org'] = file1[d]['Org']
          # This is a number; check to see if we can set it
              if c &gt;= ord('1') and c &lt;= ord(str(len(self.submenu)+1)):
                  self.option = c - ord('0') - 1 # convert keypress back to a number, then subtract 1 to get index
         # Increment or Decrement
              elif c == curses.KEY_DOWN: # down arrow
                  if self.option &lt; len(self.submenu):
                      self.option += 1
                  else: self.option = 0
              elif c == curses.KEY_UP: # up arrow
                  if self.option &gt; 0:
                      self.option -= 1
                  else: self.option = len(self.submenu)
          return self.option
  
      def __exit__(self):
          curses.endwin()
          os.system('clear')
  
  
  '''demo'''
  cm = CursedMenu()
  cm.show(['Instance-ID','Org','Tag'], title='Instance Launch', subtitle='Options')
  </code></pre>
  
  <p>It works perfectly fine if I am using the alphabets and numerics as input but not with the special keys. I have used the code below and it was working</p>
  
  <pre><code>    elif c == ord('k'): # down arrow
          if self.option &lt; len(self.submenu):
              self.option += 1
          else: self.option = 0
      elif c == ord('i'): # up arrow
          if self.option &gt; 0:
              self.option -= 1
          else: self.option = len(self.submenu)
  </code></pre>
  
  <p>Please help understand why the code is not accepting the Special Keys.</p>
  
  <p>Below is the input json I have used</p>
  
  <pre><code>{
  
     "Dept1": {
  
        "Instance Name": "instance1",
  
        "Environment": "environment1",
  
        "SystemOwner": "Owner1",
  
        "LifeCycle": "Lcy1",
  
        "DeptName": "Check1",
  
        "Org": "CSO"
  
     }
  }
  </code></pre>