add options to select primary screen and internal screen resolution
authorRalf Jung <post@ralfj.de>
Fri, 20 Jul 2012 14:52:25 +0000 (16:52 +0200)
committerRalf Jung <post@ralfj.de>
Fri, 20 Jul 2012 14:52:25 +0000 (16:52 +0200)
external_screen.py
selector_window.py

index a419908a2a95ffe8f50c55cf0645ac78b23fed2a..6d47ec725962fdc1a713a1b7f756fba9cb7ce07a 100755 (executable)
@@ -37,20 +37,31 @@ internalResolutions = connectors[internalName] # there must be a screen assoicat
 externalResolutions = connectors.get(externalName)
 
 # Check what to do
-internalArgs = ["--mode", res2str(internalResolutions[0])] # there must be a resolution for the internal screen
-externalArgs = ["--off"]
 if externalResolutions is not None: # we need to ask what to do
-       extPosition = PositionSelection(map(res2str, externalResolutions))
+       extPosition = PositionSelection(map(res2str, internalResolutions), map(res2str, externalResolutions))
        extPosition.exec_()
        if not extPosition.result(): sys.exit(1) # the user canceled
+       extResolution = res2str(externalResolutions[extPosition.extResolutions.currentIndex()])
+       intResolution = res2str(internalResolutions[extPosition.intResolutions.currentIndex()])
        # build command-line
-       externalArgs = ["--mode", extPosition.resolution] # we definitely want an external screen
-       if extPosition.position == PositionSelection.EXTERNAL_ONLY:
+       externalArgs = ["--mode", extResolution] # we definitely want an external screen
+       if extPosition.extOnly.isChecked():
                internalArgs = ["--off"]
-       elif extPosition.position == PositionSelection.LEFT:
-               externalArgs += ["--left-of", internalName]
+               externalArgs += ["--primary"]
        else:
-               externalArgs += ["--right-of", internalName]
+               # there are two screens
+               internalArgs = ["--mode", intResolution]
+               if extPosition.posLeft.isChecked():
+                       externalArgs += ["--left-of", internalName]
+               else:
+                       externalArgs += ["--right-of", internalName]
+               if extPosition.primExt.isChecked():
+                       externalArgs += ["--primary"]
+               else:
+                       internalArgs += ["--primary"]
+else:
+       internalArgs = ["--mode", res2str(internalResolutions[0]), "--primary"] # there must be a resolution for the internal screen
+       externalArgs = ["--off"]
 # and do it
 call = ["xrandr", "--output", internalName] + internalArgs + ["--output", externalName] + externalArgs
 print "Call that will be made:",call
index 0041dd7fc1399b02395f48677a1d9df67d5d631b..adee7e42c7d70d1771060e674a952e4b3e9e1cc4 100644 (file)
@@ -1,38 +1,58 @@
 #!/usr/bin/python
 from PyQt4 import QtCore, QtGui
 
-def makeLayout(parent, layout, widgets):
-       for w in widgets:
-               layout.addWidget(w)
-       parent.setLayout(layout)
+def makeLayout(layout, members):
+       for m in members:
+               if isinstance(m, QtGui.QLayout):
+                       layout.addLayout(m)
+               else:
+                       layout.addWidget(m)
+       return layout
 
 class PositionSelection(QtGui.QDialog):
        LEFT = 10
        RIGHT = 20
        EXTERNAL_ONLY = 30
        
-       def __init__(self, externalResolutions):
+       def __init__(self, internalResolutions, externalResolutions):
                # set up main window
                super(PositionSelection, self).__init__()
                self.setWindowTitle('External screen setup')
                
-               # first box: position selection
+               # position selection
                posBox = QtGui.QGroupBox('Position of external screen', self)
                self.posLeft = QtGui.QRadioButton('Left of internal screen', posBox)
                self.posRight = QtGui.QRadioButton('Right of internal screen', posBox)
                self.posRight.setChecked(True)
                self.posRight.setFocus()
                self.extOnly = QtGui.QRadioButton('Use external screen exclusively', posBox)
-               makeLayout(posBox, QtGui.QVBoxLayout(), [self.posLeft, self.posRight, self.extOnly])
+               posBox.setLayout(makeLayout(QtGui.QVBoxLayout(), [self.posLeft, self.posRight, self.extOnly]))
+               
+               # primary screen
+               primBox = QtGui.QGroupBox('Which should be the primary screen?', self)
+               self.extOnly.toggled.connect(primBox.setDisabled) # disable the box if there's just one screen in use
+               self.primExt = QtGui.QRadioButton('The external screen', primBox)
+               self.primInt = QtGui.QRadioButton('The internal screen', primBox)
+               self.primInt.setChecked(True)
+               primBox.setLayout(makeLayout(QtGui.QVBoxLayout(), [self.primExt, self.primInt]))
                
-               # second box: resolution selection
-               resBox = QtGui.QGroupBox('Resolution of external screen', self)
-               resLabel = QtGui.QLabel('Select the resolution of the external screen:', resBox)
-               self.resolutions = QtGui.QComboBox(resBox)
+               # resolution selection
+               resBox = QtGui.QGroupBox('Screen resolutions', self)
+               extResLabel = QtGui.QLabel('Resolution of external screen:', resBox)
+               self.extResolutions = QtGui.QComboBox(resBox)
                for res in externalResolutions:
-                       self.resolutions.addItem(res)
-               self.resolutions.setCurrentIndex(0) # select first resolution
-               makeLayout(resBox, QtGui.QHBoxLayout(), [resLabel, self.resolutions])
+                       self.extResolutions.addItem(res)
+               self.extResolutions.setCurrentIndex(0) # select first resolution
+               extRow = makeLayout(QtGui.QHBoxLayout(), [extResLabel, self.extResolutions])
+               intResLabel = QtGui.QLabel('Resolution of internal screen:', resBox)
+               self.extOnly.toggled.connect(intResLabel.setDisabled) # disable the label if there's just one screen in use
+               self.intResolutions = QtGui.QComboBox(resBox)
+               for res in internalResolutions:
+                       self.intResolutions.addItem(res)
+               self.intResolutions.setCurrentIndex(0) # select first resolution
+               self.extOnly.toggled.connect(self.intResolutions.setDisabled) # disable the box if there's just one screen in use
+               intRow = makeLayout(QtGui.QHBoxLayout(), [intResLabel, self.intResolutions])
+               resBox.setLayout(makeLayout(QtGui.QVBoxLayout(), [extRow, intRow]))
                
                # last row: buttons
                buttons = QtGui.QDialogButtonBox(QtGui.QDialogButtonBox.Ok | QtGui.QDialogButtonBox.Cancel, QtCore.Qt.Horizontal, self)
@@ -40,16 +60,4 @@ class PositionSelection(QtGui.QDialog):
                buttons.rejected.connect(self.reject)
                
                # add them all to the window
-               makeLayout(self, QtGui.QVBoxLayout(), [posBox, resBox, buttons])
-       
-       def accept(self):
-               # store return values
-               if self.posLeft.isChecked():
-                       self.position = PositionSelection.LEFT
-               elif self.posRight.isChecked():
-                       self.position = PositionSelection.RIGHT
-               else:
-                       self.position = PositionSelection.EXTERNAL_ONLY
-               self.resolution = str(self.resolutions.currentText())
-               # go on with default behaviour
-               super(PositionSelection, self).accept()  
+               self.setLayout(makeLayout(QtGui.QVBoxLayout(), [posBox, primBox, resBox, buttons]))