text: import os
  
  from selenium import webdriver
  
  from .Cell import Cell
  
  from ..enums.Difficulty import Difficulty
  from ..enums.DisplaySize import DisplaySize
  
  
  # Takes in URL of the Minesweeper game as a parameter
  class Controller:
      # Initialises the Controller object by getting the Chrome driver from environment variables and loading URL
      def __init__(self, url, difficulty, size, settings=(None, None, None)):
          self.url = url
          self.difficulty = difficulty
          self.size = size
          self.settings = settings
  
          options = webdriver.ChromeOptions()
          options.add_experimental_option('detach', True)
  
          self.driver = webdriver.Chrome(os.environ.get('CHROME_DRIVER'), options=options)
          self.driver.get(self.url)
  
          self.setDisplaySize(self.size)
          self.changeDifficulty(self.difficulty, self.settings)
  
      # Returns dimensions of the board from the difficulty
      def getCellDimensions(self):
          dimensions = {
              Difficulty.BEGINNER: (9, 9),
              Difficulty.INTERMEDIATE: (16, 16),
              Difficulty.EXPERT: (30, 16),
              Difficulty.CUSTOM: tuple(self.settings[0:2])
          }
  
          return dimensions[self.difficulty]
  
      # Changes difficulty depending on user's preference
      def changeDifficulty(self, difficulty, settings=(None, None, None)):
          self.difficulty = difficulty
          self.settings = settings
          self.driver.find_element('id', 'options-link').click()
          self.driver.find_element('id', difficulty.value).click()
  
          if difficulty.value == "custom":
              ids = [self.driver.find_element('id', x) for x in ['custom_' + x for x in ['height', 'width', 'mines']]]
              for i, x in enumerate(ids):
                  x.click()
                  x.clear()
                  x.send_keys(str(settings[i]))
  
          self.driver.find_element('css selector', '#options > tbody > tr:nth-child(7) > td:nth-child(1) > input').click()
  
      # Increases the display size to 200%
      def setDisplaySize(self, size):
          self.driver.find_element('id', 'display-link').click()
          self.driver.find_element('id', size.value).click()
          self.driver.find_element('id', 'display-link').click()
  
      # Gets the current display size
      def getDisplaySize(self):
          self.driver.find_element('id', 'display-link').click()
  
          out = None
          for size in DisplaySize:
              if self.driver.find_element('id', size.value).is_selected():
                  out = size
                  break
  
          self.driver.find_element('id', 'display-link').click()
          return out
  
      # Reads the given cell's value from the game
      def readCell(self, cell: Cell):
          val = self.driver.find_element('id', cell.getID()).get_attribute('class').split(' ')[1]
  
          if val == 'blank':
              return None
          elif 'bombflagged' in val:
              return 'Flag'
          elif 'bomb' in val:
              return -1
          else:
              return int(val[-1])
  
      # Click on a given cell
      def clickCell(self, cell: Cell):
          self.driver.find_element('id', cell.getID()).click()
  