2012-02-10 16:20:03 +00:00
"""
Settings is a collection of utilities to display , read & write the settings and position widgets .
"""
from __future__ import absolute_import
#Init has to be imported first because it has code to workaround the python bug where relative imports don't work if the module is imported as a main module.
import __init__
from fabmetheus_utilities import archive
from fabmetheus_utilities import euclidean
from fabmetheus_utilities import gcodec
import cStringIO
import math
import os
import shutil
import sys
import traceback
import webbrowser
try :
import Tkinter
except :
print ( ' You do not have Tkinter, which is needed for the graphical interface, you will only be able to use the command line. ' )
print ( ' Information on how to download Tkinter is at: \n www.tcl.tk/software/tcltk/ ' )
__author__ = ' Enrique Perez (perez_enrique@yahoo.com) '
__date__ = " $Date: 2008/23/04 $ "
__license__ = ' GNU Affero General Public License http://www.gnu.org/licenses/agpl.html '
globalRepositoryDialogListTable = { }
globalProfileSaveListenerListTable = { }
globalCloseListTables = [ globalRepositoryDialogListTable , globalProfileSaveListenerListTable ]
globalSettingReplacements = {
' Perimeter Width over Thickness (ratio): ' : ' Edge Width over Height (ratio): ' ,
' Layer Thickness (mm): ' : ' Layer Height (mm): ' ,
' Location Arrival X (mm): ' : ' Arrival X (mm): ' ,
' Location Arrival Y (mm): ' : ' Arrival Y (mm): ' ,
' Location Arrival Z (mm): ' : ' Arrival Z (mm): ' ,
' Location Departure X (mm): ' : ' Departure X (mm): ' ,
' Location Departure Y (mm): ' : ' Departure Y (mm): ' ,
' Location Departure Z (mm): ' : ' Departure Z (mm): ' ,
' Location Wipe X (mm): ' : ' Wipe X (mm): ' ,
' Location Wipe Y (mm): ' : ' Wipe Y (mm): ' ,
' Location Wipe Z (mm): ' : ' Wipe Z (mm): '
}
globalSpreadsheetSeparator = ' \t '
globalTemporaryOverrides = { }
def addAcceleratorCommand ( acceleratorBinding , commandFunction , master , menu , text ) :
" Add accelerator command. "
acceleratorText = acceleratorBinding [ 1 : - 1 ]
lastIndexOfMinus = acceleratorText . rfind ( ' - ' )
if lastIndexOfMinus > - 1 :
acceleratorText = acceleratorText [ : lastIndexOfMinus + 1 ] + acceleratorText [ lastIndexOfMinus + 1 : ] . capitalize ( )
acceleratorText = acceleratorText . replace ( ' KeyPress- ' , ' ' )
acceleratorText = acceleratorText . replace ( ' - ' , ' + ' )
acceleratorText = acceleratorText . replace ( ' Control ' , ' Ctrl ' )
acceleratorBinding = acceleratorBinding . replace ( ' KeyPress ' , ' ' )
menu . add_command ( accelerator = acceleratorText , label = text , underline = 0 , command = commandFunction )
master . bind ( acceleratorBinding , commandFunction )
def addEmptyRow ( gridPosition ) :
" Add an empty row. "
gridPosition . increment ( )
Tkinter . Label ( gridPosition . master ) . grid ( row = gridPosition . row , column = gridPosition . column )
def addListsToRepository ( fileNameHelp , repository ) :
' Add the value to the lists. '
addListsToRepositoryByFunction ( fileNameHelp , None , repository )
def addListsToRepositoryByFunction ( fileNameHelp , getProfileDirectory , repository ) :
' Add the value to the lists. '
repository . displayEntities = [ ]
repository . executeTitle = None
repository . fileNameHelp = fileNameHelp
repository . fileNameInput = None
repository . lowerName = fileNameHelp . split ( ' . ' ) [ - 2 ]
repository . baseName = repository . lowerName + ' .csv '
repository . baseNameSynonym = None
repository . baseNameSynonymDictionary = None
repository . capitalizedName = getEachWordCapitalized ( repository . lowerName )
repository . getProfileDirectory = getProfileDirectory
repository . openLocalHelpPage = HelpPage ( ) . getOpenFromDocumentationSubName ( repository . fileNameHelp )
repository . openWikiManualHelpPage = None
repository . preferences = [ ]
repository . repositoryDialog = None
repository . saveListenerTable = { }
repository . title = repository . capitalizedName + ' Settings '
repository . menuEntities = [ ]
repository . saveCloseTitle = ' Save and Close '
repository . windowPosition = WindowPosition ( ) . getFromValue ( repository , ' 0+0 ' )
for setting in repository . preferences :
setting . repository = repository
def addMenuEntitiesToMenu ( menu , menuEntities ) :
" Add the menu entities to the menu. "
for menuEntity in menuEntities :
menuEntity . addToMenu ( menu )
def addMenuEntitiesToMenuFrameable ( menu , menuEntities ) :
" Add the menu entities to the menu. "
for menuEntity in menuEntities :
menuEntity . addToMenuFrameable ( menu )
def addPluginsParentToMenu ( directoryPath , menu , parentPath , pluginFileNames ) :
" Add plugins and the parent to the menu. "
ToolDialog ( ) . addPluginToMenu ( menu , parentPath [ : parentPath . rfind ( ' . ' ) ] )
menu . add_separator ( )
addPluginsToMenu ( directoryPath , menu , pluginFileNames )
def addPluginsToMenu ( directoryPath , menu , pluginFileNames ) :
" Add plugins to the menu. "
for pluginFileName in pluginFileNames :
ToolDialog ( ) . addPluginToMenu ( menu , os . path . join ( directoryPath , pluginFileName ) )
def cancelRepository ( repository ) :
" Read the repository then set all the entities to the read repository values. "
getReadRepository ( repository )
for setting in repository . displayEntities :
if setting in repository . preferences :
setting . setStateToValue ( )
def deleteDirectory ( directory , subfolderName ) :
" Delete the directory if it exists. "
subDirectory = os . path . join ( directory , subfolderName )
if os . path . isdir ( subDirectory ) :
shutil . rmtree ( subDirectory )
def deleteMenuItems ( menu ) :
" Delete the menu items. "
try :
lastMenuIndex = menu . index ( Tkinter . END )
if lastMenuIndex != None :
menu . delete ( 0 , lastMenuIndex )
except :
print ( ' this should never happen, the lastMenuIndex in deleteMenuItems in settings could not be determined. ' )
def getAlongWayHexadecimalColor ( beginBrightness , colorWidth , difference , endColorTuple , wayLength ) :
" Get a color along the way from begin brightness to the end color. "
alongWay = 1.0
if wayLength != 0.0 :
alongWay = 0.4 + 0.6 * min ( 1.0 , abs ( float ( difference ) / float ( wayLength ) ) )
hexadecimalColor = ' # '
oneMinusAlongWay = 1.0 - alongWay
for primaryIndex in xrange ( 3 ) :
hexadecimalColor + = getAlongWayHexadecimalPrimary ( beginBrightness , oneMinusAlongWay , colorWidth , endColorTuple [ primaryIndex ] , alongWay )
return hexadecimalColor
def getAlongWayHexadecimalPrimary ( beginBrightness , beginRatio , colorWidth , endBrightness , endRatio ) :
" Get a primary color along the way from grey to the end color. "
brightness = beginRatio * float ( beginBrightness ) + endRatio * float ( endBrightness )
return getWidthHex ( int ( round ( brightness ) ) , colorWidth )
def getAlterationFile ( fileName ) :
" Get the file from the fileName or the lowercase fileName in the alterations directories. "
settingsAlterationsDirectory = archive . getSettingsPath ( ' alterations ' )
archive . makeDirectory ( settingsAlterationsDirectory )
fileInSettingsAlterationsDirectory = getFileInGivenDirectory ( settingsAlterationsDirectory , fileName )
if fileInSettingsAlterationsDirectory != ' ' :
return fileInSettingsAlterationsDirectory
alterationsDirectory = archive . getSkeinforgePath ( ' alterations ' )
return getFileInGivenDirectory ( alterationsDirectory , fileName )
def getAlterationFileLine ( fileName ) :
" Get the alteration file line from the fileName. "
lines = getAlterationLines ( fileName )
if len ( lines ) == 0 :
return [ ]
return getAlterationFileLineBlindly ( fileName )
def getAlterationFileLineBlindly ( fileName ) :
" Get the alteration file line from the fileName. "
return ' (<alterationFile>) %s (</alterationFile>) ' % fileName
def getAlterationFileLines ( fileName ) :
' Get the alteration file line and the text lines from the fileName in the alterations directories. '
lines = getAlterationLines ( fileName )
if len ( lines ) == 0 :
return [ ]
return [ getAlterationFileLineBlindly ( fileName ) ] + lines
def getAlterationLines ( fileName ) :
" Get the text lines from the fileName in the alterations directories. "
return archive . getTextLines ( getAlterationFile ( fileName ) )
def getDisplayedDialogFromConstructor ( repository ) :
" Display the repository dialog. "
try :
getReadRepository ( repository )
return RepositoryDialog ( repository , Tkinter . Tk ( ) )
except :
print ( ' this should never happen, getDisplayedDialogFromConstructor in settings could not open ' )
print ( repository )
traceback . print_exc ( file = sys . stdout )
return None
def getDisplayedDialogFromPath ( path ) :
" Display the repository dialog. "
pluginModule = archive . getModuleWithPath ( path )
if pluginModule == None :
return None
return getDisplayedDialogFromConstructor ( pluginModule . getNewRepository ( ) )
def getDisplayToolButtonsRepository ( directoryPath , importantFileNames , names , repository ) :
" Get the display tool buttons. "
displayToolButtons = [ ]
for name in names :
displayToolButton = DisplayToolButton ( ) . getFromPath ( name in importantFileNames , name , os . path . join ( directoryPath , name ) , repository )
displayToolButtons . append ( displayToolButton )
return displayToolButtons
def getEachWordCapitalized ( name ) :
" Get the capitalized name. "
withSpaces = name . lower ( ) . replace ( ' _ ' , ' ' )
words = withSpaces . split ( ' ' )
capitalizedStrings = [ ]
for word in words :
capitalizedStrings . append ( word . capitalize ( ) )
return ' ' . join ( capitalizedStrings )
def getFileInGivenDirectory ( directory , fileName ) :
" Get the file from the fileName or the lowercase fileName in the given directory. "
directoryListing = os . listdir ( directory )
lowerFileName = fileName . lower ( )
for directoryFile in directoryListing :
if directoryFile . lower ( ) == lowerFileName :
return getFileTextGivenDirectoryFileName ( directory , directoryFile )
return ' '
def getFileTextGivenDirectoryFileName ( directory , fileName ) :
" Get the entire text of a file with the given file name in the given directory. "
absoluteFilePath = os . path . join ( directory , fileName )
return archive . getFileText ( absoluteFilePath )
def getFolders ( directory ) :
" Get the folder list in a directory. "
archive . makeDirectory ( directory )
directoryListing = [ ]
try :
directoryListing = os . listdir ( directory )
except OSError :
print ( ' Skeinforge can not list the directory: ' )
print ( directory )
print ( ' so give it read/write permission for that directory. ' )
folders = [ ]
for fileName in directoryListing :
if os . path . isdir ( os . path . join ( directory , fileName ) ) :
folders . append ( fileName )
return folders
def getGlobalRepositoryDialogValues ( ) :
" Get the global repository dialog values. "
global globalRepositoryDialogListTable
return euclidean . getListTableElements ( globalRepositoryDialogListTable )
def getPathInFabmetheusFromFileNameHelp ( fileNameHelp ) :
" Get the directory path from file name help. "
fabmetheusPath = archive . getFabmetheusPath ( )
splitFileNameHelps = fileNameHelp . split ( ' . ' )
splitFileNameDirectoryNames = splitFileNameHelps [ : - 1 ]
for splitFileNameDirectoryName in splitFileNameDirectoryNames :
fabmetheusPath = os . path . join ( fabmetheusPath , splitFileNameDirectoryName )
return fabmetheusPath
def getProfileBaseName ( repository ) :
" Get the profile base file name. "
return getProfileName ( repository . baseName , repository )
def getProfilesDirectoryInAboveDirectory ( subName = ' ' ) :
" Get the profiles directory path in the above directory. "
aboveProfilesDirectory = archive . getSkeinforgePath ( ' profiles ' )
if subName == ' ' :
return aboveProfilesDirectory
return os . path . join ( aboveProfilesDirectory , subName )
def getProfileName ( name , repository ) :
" Get the name, joined with the profile directory if there is one. "
if repository . getProfileDirectory == None :
return name
return os . path . join ( repository . getProfileDirectory ( ) , name )
def getRadioPluginsAddPluginFrame ( directoryPath , importantFileNames , names , repository ) :
" Get the radio plugins and add the plugin frame. "
repository . pluginFrame = PluginFrame ( )
radioPlugins = [ ]
for name in names :
radioPlugin = RadioPlugin ( ) . getFromRadio ( name in importantFileNames , repository . pluginFrame . latentStringVar , name , repository , name == importantFileNames [ 0 ] )
radioPlugin . updateFunction = repository . pluginFrame . update
radioPlugins . append ( radioPlugin )
defaultRadioButton = getSelectedRadioPlugin ( importantFileNames + [ radioPlugins [ 0 ] . name ] , radioPlugins )
repository . pluginFrame . getFromPath ( defaultRadioButton , directoryPath , repository )
return radioPlugins
def getReadRepository ( repository ) :
" Read and return settings from a file. "
text = archive . getFileText ( archive . getProfilesPath ( getProfileBaseName ( repository ) ) , False )
if text == ' ' :
if repository . baseNameSynonym != None :
text = archive . getFileText ( archive . getProfilesPath ( getProfileName ( repository . baseNameSynonym , repository ) ) , False )
if text == ' ' :
print ( ' The default %s will be written in the .skeinforge_pypy folder in the home directory. ' % repository . title . lower ( ) )
text = archive . getFileText ( getProfilesDirectoryInAboveDirectory ( getProfileBaseName ( repository ) ) , False )
if text != ' ' :
readSettingsFromText ( repository , text )
writeSettings ( repository )
temporaryApplyOverrides ( repository )
return repository
readSettingsFromText ( repository , text )
temporaryApplyOverrides ( repository )
return repository
def getRepositoryText ( repository ) :
" Get the text representation of the repository. "
repositoryWriter = getRepositoryWriter ( repository . title . lower ( ) )
for setting in repository . preferences :
setting . writeToRepositoryWriter ( repositoryWriter )
return repositoryWriter . getvalue ( )
def getRepositoryWriter ( title ) :
" Get the repository writer for the title. "
repositoryWriter = cStringIO . StringIO ( )
repositoryWriter . write ( ' Format is tab separated %s . \n ' % title )
repositoryWriter . write ( ' _Name %s Value \n ' % globalSpreadsheetSeparator )
return repositoryWriter
def getSelectedPluginModuleFromPath ( filePath , plugins ) :
" Get the selected plugin module. "
for plugin in plugins :
if plugin . value :
return gcodec . getModuleFromPath ( plugin . name , filePath )
return None
def getSelectedPluginName ( plugins ) :
" Get the selected plugin name. "
for plugin in plugins :
if plugin . value :
return plugin . name
return ' '
def getSelectedRadioPlugin ( names , radioPlugins ) :
" Get the selected radio button if it exists, None otherwise. "
for radioPlugin in radioPlugins :
if radioPlugin . value :
return radioPlugin
for name in names :
for radioPlugin in radioPlugins :
if radioPlugin . name == name :
radioPlugin . value = True
return radioPlugin
print ( ' this should never happen, no getSelectedRadioPlugin in settings ' )
print ( names )
return radioPlugin [ 0 ]
def getShortestUniqueSettingName ( settingName , settings ) :
" Get the shortest unique name in the settings. "
for length in xrange ( 3 , len ( settingName ) ) :
numberOfEquals = 0
shortName = settingName [ : length ]
for setting in settings :
if setting . name [ : length ] == shortName :
numberOfEquals + = 1
if numberOfEquals < 2 :
return shortName . lower ( )
return settingName . lower ( )
def getSubfolderWithBasename ( basename , directory ) :
" Get the subfolder in the directory with the basename. "
archive . makeDirectory ( directory )
directoryListing = os . listdir ( directory )
for fileName in directoryListing :
joinedFileName = os . path . join ( directory , fileName )
if os . path . isdir ( joinedFileName ) :
if basename == fileName :
return joinedFileName
return None
def getTitleFromName ( title ) :
" Get the title of this setting. "
if title [ - 1 ] == ' : ' :
title = title [ : - 1 ]
spaceBracketIndex = title . find ( ' ( ' )
if spaceBracketIndex > - 1 :
return title [ : spaceBracketIndex ]
return title
def getUntilFirstBracket ( text ) :
' Get the text until the first bracket, if any. '
dotIndex = text . find ( ' ( ' )
if dotIndex < 0 :
return text
return text [ : dotIndex ]
def getWidthHex ( number , width ) :
" Get the first width hexadecimal digits. "
return ( ' 0000 %s ' % hex ( number ) [ 2 : ] ) [ - width : ]
def liftRepositoryDialogs ( repositoryDialogs ) :
" Lift the repository dialogs. "
for repositoryDialog in repositoryDialogs :
repositoryDialog . root . withdraw ( ) # the withdraw & deiconify trick is here because lift does not work properly on my linux computer
repositoryDialog . root . lift ( ) # probably not necessary, here in case the withdraw & deiconify trick does not work on some other computer
repositoryDialog . root . deiconify ( )
repositoryDialog . root . lift ( ) # probably not necessary, here in case the withdraw & deiconify trick does not work on some other computer
repositoryDialog . root . update_idletasks ( )
def openSVGPage ( fileName , svgViewer ) :
" Open svg page with an svg program. "
if svgViewer == ' ' :
return
if svgViewer == ' webbrowser ' :
openWebPage ( fileName )
return
filePath = ' " ' + os . path . normpath ( fileName ) + ' " ' # " to send in file name with spaces
shellCommand = svgViewer + ' ' + filePath
commandResult = os . system ( shellCommand )
if commandResult != 0 :
print ( ' It may be that the system could not find the %s program. ' % svgViewer )
print ( ' If so, try installing the %s program or look for another svg viewer, like Netscape which can be found at: ' % svgViewer )
print ( ' http://www.netscape.org/ ' )
print ( ' ' )
def openWebPage ( webPagePath ) :
" Open a web page in a browser. "
if webPagePath . find ( ' # ' ) != - 1 : # to get around # encode bug
redirectionText = ' <!DOCTYPE HTML PUBLIC " -//W3C//DTD HTML 4.0 Transitional//EN " > \n <html> \n <head> \n '
redirectionText + = ' <meta http-equiv= " REFRESH " content= " 0;url= %s " ></head> \n </HTML> \n ' % webPagePath
webPagePath = archive . getDocumentationPath ( ' redirect.html ' )
archive . writeFileText ( webPagePath , redirectionText )
webPagePath = ' " %s " ' % webPagePath # " to get around space in url bug
try : # " to get around using gnome-open or internet explorer for webbrowser default
webbrowserController = webbrowser . get ( ' firefox ' )
except :
webbrowserController = webbrowser . get ( )
webbrowserName = webbrowserController . name
if webbrowserName == ' ' :
try :
os . startfile ( webPagePath ) #this is available on some python environments, but not all
return
except :
pass
print ( ' Skeinforge was not able to open the file in a web browser. To see the documentation, open the following file in a web browser: ' )
print ( webPagePath )
return
else :
os . system ( webbrowserName + ' ' + webPagePath ) #used this instead of webbrowser.open() to workaround webbrowser open() bug
def printProgress ( layerIndex , procedureName ) :
" Print layerIndex followed by a carriage return. "
printProgressByString ( ' %s layer count %s ... ' % ( procedureName . capitalize ( ) , layerIndex + 1 ) )
def printProgressByNumber ( layerIndex , numberOfLayers , procedureName ) :
" Print layerIndex and numberOfLayers followed by a carriage return. "
printProgressByString ( ' %s layer count %s of %s ... ' % ( procedureName . capitalize ( ) , layerIndex + 1 , numberOfLayers ) )
def printProgressByString ( progressString ) :
" Print progress string. "
sys . stdout . write ( progressString )
sys . stdout . write ( chr ( 27 ) + ' \r ' )
sys . stdout . flush ( )
def quitWindow ( root ) :
" Quit a window. "
try :
root . destroy ( )
except :
pass
def quitWindows ( event = None ) :
" Quit all windows. "
global globalRepositoryDialogListTable
globalRepositoryDialogValues = euclidean . getListTableElements ( globalRepositoryDialogListTable )
for globalRepositoryDialogValue in globalRepositoryDialogValues :
quitWindow ( globalRepositoryDialogValue . root )
def readSettingsFromText ( repository , text ) :
" Read settings from a text. "
text = text . replace ( ( ' \n Name %s Value \n ' % globalSpreadsheetSeparator ) , ( ' \n _Name %s Value \n ' % globalSpreadsheetSeparator ) )
lines = archive . getTextLines ( text )
shortDictionary = { }
for setting in repository . preferences :
shortDictionary [ getShortestUniqueSettingName ( setting . name , repository . preferences ) ] = setting
if repository . baseNameSynonymDictionary != None :
synonymDictionaryCopy = repository . baseNameSynonymDictionary . copy ( )
for line in lines :
splitLine = line . split ( globalSpreadsheetSeparator )
if len ( splitLine ) > 1 :
if splitLine [ 0 ] in synonymDictionaryCopy :
del synonymDictionaryCopy [ splitLine [ 0 ] ]
for synonymDictionaryCopyKey in synonymDictionaryCopy . keys ( ) :
text = archive . getFileText ( archive . getProfilesPath ( getProfileName ( synonymDictionaryCopy [ synonymDictionaryCopyKey ] , repository ) ) , False )
synonymLines = archive . getTextLines ( text )
for synonymLine in synonymLines :
splitLine = synonymLine . split ( globalSpreadsheetSeparator )
if len ( splitLine ) > 1 :
if splitLine [ 0 ] == synonymDictionaryCopyKey :
lines . append ( synonymLine )
for lineIndex in xrange ( len ( lines ) ) :
setRepositoryToLine ( lineIndex , lines , shortDictionary )
def saveAll ( ) :
" Save all the dialogs. "
for globalRepositoryDialogValue in getGlobalRepositoryDialogValues ( ) :
globalRepositoryDialogValue . save ( )
def saveRepository ( repository ) :
" Set the entities to the dialog then write them. "
for setting in repository . preferences :
setting . setToDisplay ( )
writeSettingsPrintMessage ( repository )
for saveListener in repository . saveListenerTable . values ( ) :
saveListener ( )
def setButtonFontWeightString ( button , isBold ) :
" Set button font weight given isBold. "
try :
weightString = ' normal '
if isBold :
weightString = ' bold '
splitFont = button [ ' font ' ] . split ( )
button [ ' font ' ] = ( splitFont [ 0 ] , splitFont [ 1 ] , weightString )
except :
pass
def setEntryText ( entry , value ) :
" Set the entry text. "
if entry == None :
return
entry . delete ( 0 , Tkinter . END )
entry . insert ( 0 , str ( value ) )
def setIntegerValueToString ( integerSetting , valueString ) :
" Set the integer to the string. "
dotIndex = valueString . find ( ' . ' )
if dotIndex > - 1 :
valueString = valueString [ : dotIndex ]
try :
integerSetting . value = int ( valueString )
return
except :
print ( ' Warning, can not read integer ' + integerSetting . name + ' ' + valueString )
print ( ' Will try reading as a boolean, which might be a mistake. ' )
integerSetting . value = 0
if valueString . lower ( ) == ' true ' :
integerSetting . value = 1
def setRepositoryToLine ( lineIndex , lines , shortDictionary ) :
" Set setting dictionary to a setting line.globalSettingReplacements "
line = lines [ lineIndex ]
splitLine = line . split ( globalSpreadsheetSeparator )
if len ( splitLine ) < 2 :
return
fileSettingName = splitLine [ 0 ]
if fileSettingName in globalSettingReplacements :
fileSettingName = globalSettingReplacements [ fileSettingName ]
shortDictionaryKeys = shortDictionary . keys ( )
shortDictionaryKeys . sort ( key = len , reverse = True ) # so that a short word like fill is not overidden by a longer word like fillet
for shortDictionaryKey in shortDictionaryKeys :
if fileSettingName [ : len ( shortDictionaryKey ) ] . lower ( ) == shortDictionaryKey :
shortDictionary [ shortDictionaryKey ] . setValueToSplitLine ( lineIndex , lines , splitLine )
return
def setSpinColor ( setting ) :
" Set the spin box color to the value, yellow if it is lower than the default and blue if it is higher. "
if setting . entry == None :
return
if setting . backgroundColor == None :
setting . backgroundColor = setting . entry [ ' background ' ]
if setting . backgroundColor [ 0 ] != ' # ' :
setting . backgroundColor = ' #ffffff '
setting . colorWidth = len ( setting . backgroundColor ) / 3
setting . grey = int ( setting . backgroundColor [ 1 : 1 + setting . colorWidth ] , 16 )
setting . white = int ( ' f ' * setting . colorWidth , 16 )
if abs ( setting . value - setting . defaultValue ) < = 0.75 * setting . increment :
setting . entry [ ' background ' ] = setting . backgroundColor
return
difference = setting . value - setting . defaultValue
if difference > 0.0 :
wayLength = setting . to - setting . defaultValue
setting . entry [ ' background ' ] = getAlongWayHexadecimalColor ( setting . grey , setting . colorWidth , difference , ( 0 , setting . white , setting . white ) , wayLength )
return
wayLength = setting . from_ - setting . defaultValue
setting . entry [ ' background ' ] = getAlongWayHexadecimalColor ( setting . grey , setting . colorWidth , difference , ( setting . white , setting . white , 0 ) , wayLength )
def startMainLoopFromConstructor ( repository ) :
" Display the repository dialog and start the main loop. "
try :
import Tkinter
except :
return
displayedDialogFromConstructor = getDisplayedDialogFromConstructor ( repository )
if displayedDialogFromConstructor == None :
print ( ' Warning, displayedDialogFromConstructor in settings is none, so the window will not be displayed. ' )
else :
displayedDialogFromConstructor . root . mainloop ( )
def startMainLoopFromWindow ( window ) :
' Display the tableau window and start the main loop. '
if window == None :
return
if window . root == None :
print ( ' Warning, window.root in startMainLoopFromWindow in settings is none, so the window will not be displayed. ' )
return
window . root . mainloop ( )
def temporaryAddPreferenceOverride ( module , name , value ) :
global globalTemporaryOverrides
if not module in globalTemporaryOverrides :
globalTemporaryOverrides [ module ] = { }
globalTemporaryOverrides [ module ] [ name ] = value
print ( ' OVERRIDE %s %s %s ' % ( module , name , value ) )
print ( globalTemporaryOverrides [ module ] )
def temporaryApplyOverrides ( repository ) :
' Apply any overrides that have been set at the command line. '
# The override dictionary is a mapping of repository names to
# key-value mappings.
global globalTemporaryOverrides
if repository . baseName in globalTemporaryOverrides :
settingTable = { }
for setting in repository . preferences :
settingTable [ setting . name ] = setting
for ( name , value ) in overrides [ repository . baseName ] . items ( ) :
if name in settingTable :
settingTable [ name ] . setValueToString ( value )
else :
print ( ' Override not applied for: %s , %s ' % ( name , value ) )
def writeSettings ( repository ) :
" Write the settings to a file. "
profilesDirectoryPath = archive . getProfilesPath ( getProfileBaseName ( repository ) )
archive . makeDirectory ( os . path . dirname ( profilesDirectoryPath ) )
archive . writeFileText ( profilesDirectoryPath , getRepositoryText ( repository ) )
for setting in repository . preferences :
setting . updateSaveListeners ( )
def writeSettingsPrintMessage ( repository ) :
" Set the settings to the dialog then write them. "
writeSettings ( repository )
print ( repository . title . lower ( ) . capitalize ( ) + ' have been saved. ' )
def writeValueListToRepositoryWriter ( repositoryWriter , setting ) :
" Write tab separated name and list to the repository writer. "
repositoryWriter . write ( setting . name )
for item in setting . value :
if item != ' [] ' :
repositoryWriter . write ( globalSpreadsheetSeparator )
repositoryWriter . write ( item )
repositoryWriter . write ( ' \n ' )
class StringSetting :
" A class to display, read & write a string. "
def __init__ ( self ) :
" Set the update function to none. "
self . entry = None
self . updateFunction = None
def __repr__ ( self ) :
" Get the string representation of this StringSetting. "
return str ( self . __dict__ )
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
gridPosition . increment ( )
self . label = Tkinter . Label ( gridPosition . master , text = self . name )
self . label . grid ( row = gridPosition . row , column = 0 , columnspan = 3 , sticky = Tkinter . W )
self . createEntry ( gridPosition . master )
self . setStateToValue ( )
self . entry . grid ( row = gridPosition . row , column = 3 , columnspan = 2 , sticky = Tkinter . W )
self . bindEntry ( )
LabelHelp ( self . repository . fileNameHelp , gridPosition . master , self . name , self . label )
def addToMenu ( self , repositoryMenu ) :
" Do nothing because this should only be added to a frameable repository menu. "
pass
def addToMenuFrameable ( self , repositoryMenu ) :
" Add this to the frameable repository menu. "
titleFromName = getTitleFromName ( self . name )
helpWindowMenu = Tkinter . Menu ( repositoryMenu , tearoff = 0 )
repositoryMenu . add_cascade ( label = titleFromName , menu = helpWindowMenu , underline = 0 )
if self . name in self . repository . frameList . value :
helpWindowMenu . add_command ( label = ' Remove from Window ' , command = self . removeFromWindow )
else :
helpWindowMenu . add_command ( label = ' Add to Window ' , command = self . addToWindow )
helpWindowMenu . add_separator ( )
helpWindowMenu . add_command ( label = ' Help ' , command = HelpPage ( ) . getOpenFromDocumentationSubName ( self . repository . fileNameHelp + ' # ' + titleFromName ) )
def addToWindow ( self ) :
" Add this to the repository frame list. "
self . repository . frameList . addToList ( self . name )
def bindEntry ( self ) :
" Bind the entry to the update function. "
if self . updateFunction != None :
self . entry . bind ( ' <Return> ' , self . updateFunction )
def createEntry ( self , root ) :
" Create the entry. "
self . entry = Tkinter . Entry ( root )
def getFromValue ( self , name , repository , value ) :
" Initialize. "
return self . getFromValueOnlyAddToRepository ( name , repository , value )
def getFromValueOnly ( self , name , repository , value ) :
" Initialize. "
self . defaultValue = value
self . name = name
self . repository = repository
self . value = value
return self
def getFromValueOnlyAddToRepository ( self , name , repository , value ) :
" Initialize. "
repository . displayEntities . append ( self )
repository . menuEntities . append ( self )
repository . preferences . append ( self )
return self . getFromValueOnly ( name , repository , value )
def removeFromWindow ( self ) :
" Remove this from the repository frame list. "
self . repository . frameList . removeFromList ( self . name )
def setStateToValue ( self ) :
" Set the entry to the value. "
setEntryText ( self . entry , self . value )
def setToDisplay ( self ) :
" Set the string to the entry field. "
try :
valueString = self . entry . get ( )
self . setValueToString ( valueString )
except :
pass
def setUpdateFunction ( self , updateFunction ) :
" Set the update function. "
self . updateFunction = updateFunction
def setValueToSplitLine ( self , lineIndex , lines , splitLine ) :
" Set the value to the second word of a split line. "
self . setValueToString ( splitLine [ 1 ] )
def setValueToString ( self , valueString ) :
" Set the value to the value string. "
self . value = valueString
def updateSaveListeners ( self ) :
" Update save listeners if any. "
pass
def writeToRepositoryWriter ( self , repositoryWriter ) :
" Write tab separated name and value to the repository writer. "
repositoryWriter . write ( ' %s %s %s \n ' % ( self . name , globalSpreadsheetSeparator , self . value ) )
class BooleanSetting ( StringSetting ) :
" A class to display, read & write a boolean. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
gridPosition . increment ( )
self . checkbutton = Tkinter . Checkbutton ( gridPosition . master , command = self . toggleCheckbutton , text = self . name )
#toggleCheckbutton is being used instead of a Tkinter IntVar because there is a weird bug where it doesn't work properly if this setting is not on the first window.
self . checkbutton . grid ( row = gridPosition . row , columnspan = 5 , sticky = Tkinter . W )
self . setStateToValue ( )
LabelHelp ( self . repository . fileNameHelp , gridPosition . master , self . name , self . checkbutton )
def addToMenu ( self , repositoryMenu ) :
" Add this to the repository menu. "
self . activateToggleMenuCheckbutton = False
#activateToggleMenuCheckbutton is being used instead of setting command after because add_checkbutton does not return a checkbutton.
repositoryMenu . add_checkbutton ( label = getTitleFromName ( self . name ) , command = self . toggleMenuCheckbutton )
if self . value :
repositoryMenu . invoke ( repositoryMenu . index ( Tkinter . END ) )
self . activateToggleMenuCheckbutton = True
def addToMenuFrameable ( self , repositoryMenu ) :
" Add this to the frameable repository menu. "
titleFromName = getTitleFromName ( self . name )
helpWindowMenu = Tkinter . Menu ( repositoryMenu , tearoff = 0 )
repositoryMenu . add_cascade ( label = titleFromName , menu = helpWindowMenu , underline = 0 )
self . addToMenu ( helpWindowMenu )
helpWindowMenu . add_separator ( )
helpWindowMenu . add_command ( label = ' Help ' , command = HelpPage ( ) . getOpenFromDocumentationSubName ( self . repository . fileNameHelp + ' # ' + titleFromName ) )
def setStateToValue ( self ) :
" Set the checkbutton to the boolean. "
try :
if self . value :
self . checkbutton . select ( )
else :
self . checkbutton . deselect ( )
except :
pass
def setToDisplay ( self ) :
" Do nothing because toggleCheckbutton is handling the value. "
pass
def setValueToString ( self , valueString ) :
" Set the boolean to the string. "
self . value = ( valueString . lower ( ) == ' true ' )
def toggleCheckbutton ( self ) :
" Workaround for Tkinter bug, toggle the value. "
self . value = not self . value
self . setStateToValue ( )
if self . updateFunction != None :
self . updateFunction ( )
def toggleMenuCheckbutton ( self ) :
" Workaround for Tkinter bug, toggle the value. "
if self . activateToggleMenuCheckbutton :
self . value = not self . value
if self . updateFunction != None :
self . updateFunction ( )
class CloseListener :
" A class to listen to link a window to the global repository dialog list table. "
def __init__ ( self , window , closeFunction = None ) :
" Add the window to the global repository dialog list table. "
self . closeFunction = closeFunction
self . window = window
self . shouldWasClosedBeBound = True
global globalRepositoryDialogListTable
euclidean . addElementToListDictionaryIfNotThere ( window , window , globalRepositoryDialogListTable )
def listenToWidget ( self , widget ) :
" Listen to the destroy message of the widget. "
if self . shouldWasClosedBeBound :
self . shouldWasClosedBeBound = False
widget . bind ( ' <Destroy> ' , self . wasClosed )
def wasClosed ( self , event ) :
" The dialog was closed. "
global globalCloseListTables
for globalCloseListTable in globalCloseListTables :
if self . window in globalCloseListTable :
del globalCloseListTable [ self . window ]
if self . closeFunction != None :
self . closeFunction ( )
class DisplayToolButton :
" A class to display the tool dialog button, in a two column wide table. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
self . displayButton = Tkinter . Button ( gridPosition . master , activebackground = ' black ' , activeforeground = ' white ' , text = getEachWordCapitalized ( self . name ) , command = self . displayDialog )
setButtonFontWeightString ( self . displayButton , self . important )
gridPosition . incrementGivenNumberOfColumns ( 2 )
self . displayButton . grid ( row = gridPosition . row , column = gridPosition . column , columnspan = 2 )
def displayDialog ( self ) :
" Display function. "
ToolDialog ( ) . getFromPath ( self . path ) . display ( )
def getFromPath ( self , important , name , path , repository ) :
" Initialize. "
self . important = important
self . name = name
self . path = path
self . repository = repository
repository . displayEntities . append ( self )
return self
class FileHelpMenuBar :
def __init__ ( self , root ) :
" Create a menu bar with a file and help menu. "
self . underlineLetters = [ ]
self . menuBar = Tkinter . Menu ( root )
self . root = root
root . config ( menu = self . menuBar )
self . fileMenu = Tkinter . Menu ( self . menuBar , tearoff = 0 )
self . menuBar . add_cascade ( label = " File " , menu = self . fileMenu , underline = 0 )
self . underlineLetters . append ( ' f ' )
def addMenuToMenuBar ( self , labelText , menu ) :
" Add a menu to the menu bar. "
lowerLabelText = labelText . lower ( )
for underlineLetterIndex in xrange ( len ( lowerLabelText ) ) :
underlineLetter = lowerLabelText [ underlineLetterIndex ]
if underlineLetter not in self . underlineLetters :
self . underlineLetters . append ( underlineLetter )
self . menuBar . add_cascade ( label = labelText , menu = menu , underline = underlineLetterIndex )
return
self . menuBar . add_cascade ( label = labelText , menu = menu )
def addPluginToMenuBar ( self , modulePath , repository , window ) :
" Add a menu to the menu bar from a tool. "
pluginModule = archive . getModuleWithPath ( modulePath )
if pluginModule == None :
print ( ' this should never happen, pluginModule in addMenuToMenuBar in settings is None. ' )
return None
repositoryMenu = Tkinter . Menu ( self . menuBar , tearoff = 0 )
labelText = getEachWordCapitalized ( os . path . basename ( modulePath ) )
self . addMenuToMenuBar ( labelText , repositoryMenu )
pluginModule . addToMenu ( self . root , repositoryMenu , repository , window )
def completeMenu ( self , closeFunction , repository , saveFunction , window ) :
" Complete the menu. "
self . closeFunction = closeFunction
self . saveFunction = saveFunction
addAcceleratorCommand ( ' <Control-KeyPress-s> ' , saveFunction , self . root , self . fileMenu , ' Save ' )
self . fileMenu . add_command ( label = " Save and Close " , command = self . saveClose )
addAcceleratorCommand ( ' <Control-KeyPress-w> ' , closeFunction , self . root , self . fileMenu , ' Close ' )
self . fileMenu . add_separator ( )
addAcceleratorCommand ( ' <Control-KeyPress-q> ' , quitWindows , self . root , self . fileMenu , ' Quit ' )
skeinforgePluginsPath = archive . getSkeinforgePath ( ' skeinforge_plugins ' )
pluginFileNames = archive . getPluginFileNamesFromDirectoryPath ( skeinforgePluginsPath )
2012-02-13 16:29:58 +00:00
#for pluginFileName in pluginFileNames:
# self.addPluginToMenuBar(os.path.join(skeinforgePluginsPath, pluginFileName), repository, window)
2012-02-10 16:20:03 +00:00
def saveClose ( self ) :
" Call the save function then the close function. "
self . saveFunction ( )
self . closeFunction ( )
class FileNameInput ( StringSetting ) :
" A class to display, read & write a fileName. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
self . gridPosition = gridPosition
gridPosition . executables . append ( self )
def execute ( self ) :
" Open the file picker. "
self . wasCancelled = False
parent = self . gridPosition . master
try :
import tkFileDialog
summarized = archive . getSummarizedFileName ( self . value )
initialDirectory = os . path . dirname ( summarized )
if len ( initialDirectory ) > 0 :
initialDirectory + = os . sep
else :
initialDirectory = " . "
fileName = tkFileDialog . askopenfilename ( filetypes = self . getFileNameFirstTypes ( ) , initialdir = initialDirectory , initialfile = os . path . basename ( summarized ) , parent = parent , title = self . name )
self . setCancelledValue ( fileName )
return
except :
print ( ' Could not get the old directory in settings, so the file picker will be opened in the default directory. ' )
try :
fileName = tkFileDialog . askopenfilename ( filetypes = self . getFileNameFirstTypes ( ) , initialdir = ' . ' , initialfile = ' ' , parent = parent , title = self . name )
self . setCancelledValue ( fileName )
except :
print ( ' Error in execute in FileName in settings, ' + self . name )
def getFileNameFirstTypes ( self ) :
" Get the file types with the file type of the fileName moved to the front of the list. "
allFiles = [ ( ' All ' , ' *.* ' ) ]
try :
basename = os . path . basename ( self . value )
splitFile = basename . split ( ' . ' )
allReadables = [ ]
if len ( self . fileTypes ) > 1 :
for fileType in self . fileTypes :
allReadable = ( ( ' All Readable ' , fileType [ 1 ] ) )
allReadables . append ( allReadable )
if len ( splitFile ) < 1 :
return allReadables + allFiles + self . fileTypes
baseExtension = splitFile [ - 1 ]
for fileType in self . fileTypes :
fileExtension = fileType [ 1 ] . split ( ' . ' ) [ - 1 ]
if fileExtension == baseExtension :
fileNameFirstTypes = self . fileTypes [ : ]
fileNameFirstTypes . remove ( fileType )
return [ fileType ] + allReadables + allFiles + fileNameFirstTypes
return allReadables + allFiles + self . fileTypes
except :
return allFiles
def getFromFileName ( self , fileTypes , name , repository , value ) :
" Initialize. "
self . getFromValueOnly ( name , repository , value )
self . fileTypes = fileTypes
self . wasCancelled = False
repository . displayEntities . append ( self )
repository . preferences . append ( self )
return self
def setCancelledValue ( self , fileName ) :
" Set the value to the file name and wasCancelled true if a file was not picked. "
if ( str ( fileName ) == ' () ' or str ( fileName ) == ' ' ) :
self . wasCancelled = True
else :
self . value = fileName
def setToDisplay ( self ) :
" Do nothing because the file dialog is handling the value. "
pass
class FloatSetting ( StringSetting ) :
" A class to display, read & write a float. "
def setValueToString ( self , valueString ) :
" Set the float to the string. "
try :
self . value = float ( valueString )
except :
print ( ' Oops, can not read float ' + self . name + ' ' + valueString )
class FloatSpin ( FloatSetting ) :
" A class to display, read & write an float in a spin box. "
def addToMenuFrameable ( self , repositoryMenu ) :
" Add this to the frameable repository menu. "
titleFromName = getTitleFromName ( self . name )
helpWindowMenu = Tkinter . Menu ( repositoryMenu , tearoff = 0 )
repositoryMenu . add_cascade ( label = titleFromName , menu = helpWindowMenu , underline = 0 )
if self . name in self . repository . frameList . value :
helpWindowMenu . add_command ( label = ' Remove from Window ' , command = self . removeFromWindow )
else :
helpWindowMenu . add_command ( label = ' Add to Window ' , command = self . addToWindow )
helpWindowMenu . add_separator ( )
changeString = ' by %s ' % self . increment
helpWindowMenu . add_command ( label = ' Increase ' + changeString , command = self . increase )
helpWindowMenu . add_command ( label = ' Decrease ' + changeString , command = self . decrease )
helpWindowMenu . add_separator ( )
helpWindowMenu . add_command ( label = ' Help ' , command = HelpPage ( ) . getOpenFromDocumentationSubName ( self . repository . fileNameHelp + ' # ' + titleFromName ) )
def bindEntry ( self ) :
" Bind the entry to the update function. "
self . entry . bind ( ' <Return> ' , self . entryUpdated )
self . setColor ( )
def createEntry ( self , root ) :
" Create the entry. "
self . entry = Tkinter . Spinbox ( root , command = self . setColorToDisplay , from_ = self . from_ , increment = self . increment , to = self . to )
def decrease ( self ) :
" Decrease the value then set the state and color to the value. "
self . value - = self . increment
self . setStateUpdateColor ( )
def entryUpdated ( self , event = None ) :
" Create the entry. "
self . setColorToDisplay ( )
if self . updateFunction != None :
self . updateFunction ( event )
def getFromValue ( self , from_ , name , repository , to , value ) :
" Initialize. "
self . backgroundColor = None
self . from_ = from_
self . minimumWidth = min ( value - from_ , to - value )
rank = euclidean . getRank ( 0.05 * ( to - from_ ) )
self . increment = euclidean . getIncrementFromRank ( rank )
self . to = to
return self . getFromValueOnlyAddToRepository ( name , repository , value )
def increase ( self ) :
" Increase the value then set the state and color to the value. "
self . value + = self . increment
self . setStateUpdateColor ( )
def setColor ( self , event = None ) :
" Set the color to the value, yellow if it is lower than the default and blue if it is higher. "
setSpinColor ( self )
def setColorToDisplay ( self , event = None ) :
" Set the color to the value, yellow if it is lower than the default and blue if it is higher. "
self . setToDisplay ( )
self . setColor ( )
def setStateToValue ( self ) :
" Set the entry to the value. "
setEntryText ( self . entry , self . value )
self . setColor ( )
def setStateUpdateColor ( self ) :
" Set the state to the value, call the update function, then set the color. "
self . setStateToValue ( )
if self . updateFunction != None :
self . updateFunction ( )
class FloatSpinNotOnMenu ( FloatSpin ) :
" A class to display, read & write an float in a spin box, which is not to be added to a menu. "
def getFromValueOnlyAddToRepository ( self , name , repository , value ) :
" Initialize. "
repository . displayEntities . append ( self )
repository . preferences . append ( self )
return self . getFromValueOnly ( name , repository , value )
class FloatSpinUpdate ( FloatSpin ) :
" A class to display, read, update & write an float in a spin box. "
def createEntry ( self , root ) :
" Create the entry. "
self . entry = Tkinter . Spinbox ( root , command = self . entryUpdated , from_ = self . from_ , increment = self . increment , to = self . to )
class FrameList :
" A class to list the frames. "
def addToList ( self , word ) :
" Add the word to the sorted list. "
self . value . append ( word )
self . value . sort ( )
self . repository . window . redisplayWindowUpdate ( )
def getFromValue ( self , name , repository , value ) :
" Initialize. "
repository . preferences . append ( self )
self . name = name
self . repository = repository
self . value = value
return self
def removeFromList ( self , word ) :
" Remove the word from the sorted list. "
self . value . remove ( word )
self . value . sort ( )
self . repository . window . redisplayWindowUpdate ( )
def setToDisplay ( self ) :
" Do nothing because frame list does not have a display. "
pass
def setValueToSplitLine ( self , lineIndex , lines , splitLine ) :
" Set the value to the second and later words of a split line. "
self . value = splitLine [ 1 : ]
def updateSaveListeners ( self ) :
" Update save listeners if any. "
pass
def writeToRepositoryWriter ( self , repositoryWriter ) :
" Write tab separated name and list to the repository writer. "
writeValueListToRepositoryWriter ( repositoryWriter , self )
class GridHorizontal :
" A class to place elements horizontally on a grid. "
def __init__ ( self , column , row ) :
" Initialize the column and row. "
self . column = column
self . columnStart = column
self . row = row
def getCopy ( self ) :
" Get a copy. "
copy = GridHorizontal ( self . column , self . row )
copy . columnStart = self . columnStart
return copy
def increment ( self ) :
" Increment the position horizontally. "
self . column + = 1
class GridVertical :
" A class to place elements vertically on a grid. "
def __init__ ( self , column , row ) :
" Initialize the column and row. "
self . column = column
self . columnOffset = column
self . columnStart = column
self . row = row
self . rowStart = row
def execute ( self ) :
" The execute button was clicked. "
for executable in self . executables :
executable . execute ( )
saveAll ( )
self . repository . execute ( )
def getCopy ( self ) :
" Get a copy. "
copy = GridVertical ( self . column , self . row )
copy . columnOffset = self . columnOffset
copy . columnStart = self . columnStart
copy . rowStart = self . rowStart
return copy
def increment ( self ) :
" Increment the position vertically. "
self . column = self . columnStart
self . columnOffset = self . columnStart
self . row + = 1
def incrementGivenNumberOfColumns ( self , numberOfColumns ) :
" Increment the position vertically and offset it horizontally by the given number of columns. "
self . column = self . columnOffset
if self . columnOffset == self . columnStart :
self . columnOffset = self . columnStart + 1
self . row + = 1
return
if self . columnOffset < self . columnStart + numberOfColumns - 1 :
self . columnOffset + = 1
return
self . columnOffset = self . columnStart
def setExecutablesRepository ( self , repository ) :
" Set the executables to an empty list and set the repository. "
self . executables = [ ]
self . repository = repository
class HelpPage :
" A class to open a help page. "
def __init__ ( self ) :
" Initialize column. "
self . column = 3
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
capitalizedName = getEachWordCapitalized ( self . name )
self . displayButton = Tkinter . Button ( gridPosition . master , activebackground = ' black ' , activeforeground = ' white ' , command = self . openPage , text = capitalizedName )
if len ( capitalizedName ) < 12 :
self . displayButton [ ' width ' ] = 10
self . displayButton . grid ( row = gridPosition . row , column = self . column , columnspan = 2 )
def addToMenu ( self , repositoryMenu ) :
" Add this to the repository menu. "
repositoryMenu . add_command ( label = getTitleFromName ( self . name ) , command = self . openPage )
def addToMenuFrameable ( self , repositoryMenu ) :
" Add this to the frameable repository menu. "
self . addToMenu ( repositoryMenu )
def getFromNameAfterHTTP ( self , afterHTTP , name , repository ) :
" Initialize. "
self . setToNameRepository ( name , repository )
self . hypertextAddress = ' http:// ' + afterHTTP
return self
def getFromNameAfterWWW ( self , afterWWW , name , repository ) :
" Initialize. "
self . setToNameRepository ( name , repository )
self . hypertextAddress = ' http://www. ' + afterWWW
return self
def getFromNameSubName ( self , name , repository , subName = ' ' ) :
" Initialize. "
self . setToNameRepository ( name , repository )
self . hypertextAddress = archive . getDocumentationPath ( subName )
return self
def getOpenFromAbsolute ( self , hypertextAddress ) :
" Get the open help page function from the hypertext address. "
self . hypertextAddress = hypertextAddress
return self . openPage
def getOpenFromAfterHTTP ( self , afterHTTP ) :
" Get the open help page function from the part of the address after the HTTP. "
self . hypertextAddress = ' http:// ' + afterHTTP
return self . openPage
def getOpenFromAfterWWW ( self , afterWWW ) :
" Get the open help page function from the afterWWW of the address after the www. "
self . hypertextAddress = ' http://www. ' + afterWWW
return self . openPage
def getOpenFromDocumentationSubName ( self , subName = ' ' ) :
" Get the open help page function from the afterWWW of the address after the www. "
self . hypertextAddress = archive . getDocumentationPath ( subName )
return self . openPage
def openPage ( self , event = None ) :
" Open the browser to the hypertext address. "
openWebPage ( self . hypertextAddress )
def setToNameRepository ( self , name , repository ) :
" Set to the name and repository. "
self . name = name
self . repository = repository
repository . displayEntities . append ( self )
repository . menuEntities . append ( self )
class HelpPageRepository :
" A class to open a repository help page. "
def __init__ ( self , repository ) :
" Add this to the dialog. "
self . repository = repository
def openPage ( self , event = None ) :
" Open the browser to the repository help page. "
if self . repository . openWikiManualHelpPage == None :
self . repository . openLocalHelpPage ( )
return
from skeinforge_application . skeinforge_utilities import skeinforge_help
helpRepository = getReadRepository ( skeinforge_help . HelpRepository ( ) )
if helpRepository . wikiManualPrimary . value :
self . repository . openWikiManualHelpPage ( )
return
self . repository . openLocalHelpPage ( )
class IntSetting ( FloatSetting ) :
" A class to display, read & write an int. "
def setValueToString ( self , valueString ) :
" Set the integer to the string. "
setIntegerValueToString ( self , valueString )
class IntSpin ( FloatSpin ) :
" A class to display, read & write an int in a spin box. "
def getFromValue ( self , from_ , name , repository , to , value ) :
" Initialize. "
self . backgroundColor = None
self . from_ = from_
rank = euclidean . getRank ( 0.05 * ( to - from_ ) )
self . increment = max ( 1 , int ( euclidean . getIncrementFromRank ( rank ) ) )
self . minimumWidth = min ( value - from_ , to - value )
self . to = to
return self . getFromValueOnlyAddToRepository ( name , repository , value )
def getSingleIncrementFromValue ( self , from_ , name , repository , to , value ) :
" Initialize. "
self . backgroundColor = None
self . from_ = from_
self . increment = 1
self . minimumWidth = min ( value - from_ , to - value )
self . to = to
return self . getFromValueOnlyAddToRepository ( name , repository , value )
def setValueToString ( self , valueString ) :
" Set the integer to the string. "
setIntegerValueToString ( self , valueString )
class IntSpinNotOnMenu ( IntSpin ) :
" A class to display, read & write an integer in a spin box, which is not to be added to a menu. "
def getFromValueOnlyAddToRepository ( self , name , repository , value ) :
" Initialize. "
repository . displayEntities . append ( self )
repository . preferences . append ( self )
return self . getFromValueOnly ( name , repository , value )
class IntSpinUpdate ( IntSpin ) :
" A class to display, read, update & write an int in a spin box. "
def createEntry ( self , root ) :
" Create the entry. "
self . entry = Tkinter . Spinbox ( root , command = self . entryUpdated , from_ = self . from_ , increment = self . increment , to = self . to )
class LabelDisplay :
" A class to add a label. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
gridPosition . increment ( )
self . label = Tkinter . Label ( gridPosition . master , text = self . name )
self . label . grid ( row = gridPosition . row , column = 0 , columnspan = self . columnspan , sticky = Tkinter . W )
LabelHelp ( self . repository . fileNameHelp , gridPosition . master , self . name , self . label )
def getFromName ( self , name , repository ) :
" Initialize. "
self . columnspan = 3
self . name = name
self . repository = repository
repository . displayEntities . append ( self )
return self
class LabelHelp :
" A class to add help to a widget. "
def __init__ ( self , fileNameHelp , master , name , widget ) :
" Add menu to the widget. "
if len ( name ) < 1 :
return
self . popupMenu = Tkinter . Menu ( master , tearoff = 0 )
titleFromName = getTitleFromName ( name . replace ( ' - ' , ' ' ) . replace ( ' - ' , ' ' ) )
self . popupMenu . add_command ( label = ' Help ' , command = HelpPage ( ) . getOpenFromDocumentationSubName ( fileNameHelp + ' # ' + titleFromName ) )
widget . bind ( ' <Button-1> ' , self . unpostPopupMenu )
widget . bind ( ' <Button-2> ' , self . unpostPopupMenu )
widget . bind ( ' <Button-3> ' , self . displayPopupMenu )
def displayPopupMenu ( self , event = None ) :
' Display the popup menu when the button is right clicked. '
try :
self . popupMenu . tk_popup ( event . x_root + 30 , event . y_root , 0 )
finally :
self . popupMenu . grab_release ( )
def unpostPopupMenu ( self , event = None ) :
' Unpost the popup menu. '
self . popupMenu . unpost ( )
class LabelSeparator :
" A class to add a label and menu separator. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
gridPosition . increment ( )
self . label = Tkinter . Label ( gridPosition . master , text = ' ' )
self . label . grid ( row = gridPosition . row , column = 0 , columnspan = 3 , sticky = Tkinter . W )
def addToMenu ( self , repositoryMenu ) :
" Add this to the repository menu. "
repositoryMenu . add_separator ( )
def addToMenuFrameable ( self , repositoryMenu ) :
" Add this to the frameable repository menu. "
self . addToMenu ( repositoryMenu )
def getFromRepository ( self , repository ) :
" Initialize. "
self . name = ' '
self . repository = repository
repository . displayEntities . append ( self )
repository . menuEntities . append ( self )
return self
class LatentStringVar :
" A class to provide a StringVar when needed. "
def __init__ ( self ) :
" Set the string var. "
self . stringVar = None
def getString ( self ) :
" Get the string. "
return self . getVar ( ) . get ( )
def getVar ( self ) :
" Get the string var. "
if self . stringVar == None :
self . stringVar = Tkinter . StringVar ( )
return self . stringVar
def setString ( self , word ) :
" Set the string. "
self . getVar ( ) . set ( word )
class LayerCount :
' A class to handle the layerIndex. '
def __init__ ( self ) :
' Initialize. '
self . layerIndex = - 1
def __repr__ ( self ) :
' Get the string representation of this LayerCount. '
return str ( self . layerIndex )
def printProgressIncrement ( self , procedureName ) :
' Print progress then increment layerIndex. '
self . layerIndex + = 1
printProgress ( self . layerIndex , procedureName )
class MenuButtonDisplay :
" A class to add a menu button. "
def addRadiosToDialog ( self , gridPosition ) :
" Add the menu radios to the dialog. "
for menuRadio in self . menuRadios :
menuRadio . addToDialog ( gridPosition )
def addToMenu ( self , repositoryMenu ) :
" Add this to the repository menu. "
if len ( self . menuRadios ) < 1 :
print ( ' The MenuButtonDisplay in settings should have menu items. ' )
print ( self . name )
return
self . menu = Tkinter . Menu ( repositoryMenu , tearoff = 0 )
repositoryMenu . add_cascade ( label = getTitleFromName ( self . name ) , menu = self . menu )
self . setRadioVarToName ( self . menuRadios [ 0 ] . name )
def addToMenuFrameable ( self , repositoryMenu ) :
" Add this to the frameable repository menu. "
titleFromName = getTitleFromName ( self . name )
self . addToMenu ( repositoryMenu )
self . menu . add_command ( label = ' Help ' , command = HelpPage ( ) . getOpenFromDocumentationSubName ( self . repository . fileNameHelp + ' # ' + titleFromName ) )
self . menu . add_separator ( )
def getFromName ( self , name , repository ) :
" Initialize. "
self . columnspan = 2
self . menuRadios = [ ]
self . name = name
self . radioVar = None
self . repository = repository
repository . menuEntities . append ( self )
return self
def removeMenus ( self ) :
" Remove all menus. "
deleteMenuItems ( self . menu )
self . menuRadios = [ ]
def setRadioVarToName ( self , name ) :
" Get the menu button. "
self . optionList = [ name ]
self . radioVar = Tkinter . StringVar ( )
self . radioVar . set ( self . optionList [ 0 ] )
def setToNameAddToDialog ( self , name , gridPosition ) :
" Get the menu button. "
if self . radioVar != None :
return
gridPosition . increment ( )
self . setRadioVarToName ( name )
self . label = Tkinter . Label ( gridPosition . master , text = self . name )
self . label . grid ( row = gridPosition . row , column = 0 , columnspan = 3 , sticky = Tkinter . W )
self . menuButton = Tkinter . OptionMenu ( gridPosition . master , self . radioVar , self . optionList )
self . menuButton . grid ( row = gridPosition . row , column = 3 , columnspan = self . columnspan , sticky = Tkinter . W )
self . menuButton . menu = Tkinter . Menu ( self . menuButton , tearoff = 0 )
self . menu = self . menuButton . menu
self . menuButton [ ' menu ' ] = self . menu
LabelHelp ( self . repository . fileNameHelp , gridPosition . master , self . name , self . label )
class MenuRadio ( BooleanSetting ) :
" A class to display, read & write a boolean with associated menu radio button. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
self . menuButtonDisplay . setToNameAddToDialog ( self . name , gridPosition )
self . addToSubmenu ( )
def addToMenu ( self , repositoryMenu ) :
" Add this to the submenu set by MenuButtonDisplay, the repository menu is ignored "
self . addToSubmenu ( )
def addToMenuFrameable ( self , repositoryMenu ) :
" Add this to the frameable repository menu. "
self . addToMenu ( repositoryMenu )
def addToSubmenu ( self ) :
" Add this to the submenu. "
self . activate = False
menu = self . menuButtonDisplay . menu
menu . add_radiobutton ( label = self . name , command = self . clickRadio , value = self . name , variable = self . menuButtonDisplay . radioVar )
self . menuLength = menu . index ( Tkinter . END )
if self . value :
self . menuButtonDisplay . radioVar . set ( self . name )
self . invoke ( )
self . activate = True
def clickRadio ( self ) :
" Workaround for Tkinter bug, invoke and set the value when clicked. "
if not self . activate :
return
self . menuButtonDisplay . radioVar . set ( self . name )
if self . updateFunction != None :
self . updateFunction ( )
def getFromMenuButtonDisplay ( self , menuButtonDisplay , name , repository , value ) :
" Initialize. "
self . getFromValueOnlyAddToRepository ( name , repository , value )
self . menuButtonDisplay = menuButtonDisplay
self . menuButtonDisplay . menuRadios . append ( self )
return self
def invoke ( self ) :
" Workaround for Tkinter bug, invoke to set the value when changed. "
self . menuButtonDisplay . menu . invoke ( self . menuLength )
def setStateToValue ( self ) :
" Set the checkbutton to the boolean. "
try :
if self . value :
self . invoke ( )
except :
pass
def setToDisplay ( self ) :
" Set the boolean to the checkbutton. "
if self . menuButtonDisplay . radioVar != None :
self . value = ( self . menuButtonDisplay . radioVar . get ( ) == self . name )
class PluginFrame :
" A class to display the plugins in a frame. "
def __init__ ( self ) :
" Initialize. "
self . gridTable = { }
self . latentStringVar = LatentStringVar ( )
self . oldLatentString = ' '
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
gridPosition . increment ( )
self . gridPosition = gridPosition . getCopy ( )
self . gridPosition . master = gridPosition . master
self . createFrame ( gridPosition )
def createFrame ( self , gridPosition ) :
" Create the frame. "
gridVertical = GridVertical ( 0 , 0 )
gridVertical . master = Tkinter . LabelFrame ( gridPosition . master , borderwidth = 3 , relief = ' raised ' )
gridVertical . master . grid ( row = gridPosition . row , column = gridPosition . column , columnspan = 12 , sticky = Tkinter . E + Tkinter . W + Tkinter . N + Tkinter . S )
gridPosition . master . grid_rowconfigure ( gridPosition . row , weight = 1 )
gridPosition . master . grid_columnconfigure ( gridPosition . column + 11 , weight = 1 )
if self . latentStringVar . getString ( ) == ' ' :
self . defaultRadioButton . setSelect ( )
self . gridTable [ self . latentStringVar . getString ( ) ] = gridVertical
path = os . path . join ( self . directoryPath , self . latentStringVar . getString ( ) )
pluginModule = archive . getModuleWithPath ( path )
if pluginModule == None :
print ( ' this should never happen, pluginModule in addToDialog in PluginFrame in settings is None ' )
print ( path )
return
gridVertical . repository = getReadRepository ( pluginModule . getNewRepository ( ) )
gridVertical . frameGridVertical = GridVertical ( 0 , 0 )
gridVertical . frameGridVertical . setExecutablesRepository ( gridVertical . repository )
executeTitle = gridVertical . repository . executeTitle
2012-02-13 13:24:55 +00:00
#if executeTitle != None:
# executeButton = Tkinter.Button( gridVertical.master, activebackground = 'black', activeforeground = 'blue', text = executeTitle, command = gridVertical.frameGridVertical.execute )
# executeButton.grid( row = gridVertical.row, column = gridVertical.column, sticky = Tkinter.W )
# gridVertical.column += 1
2012-02-10 16:20:03 +00:00
self . helpButton = Tkinter . Button ( gridVertical . master , activebackground = ' black ' , activeforeground = ' white ' , text = " ? " , command = HelpPageRepository ( gridVertical . repository ) . openPage )
self . helpButton . grid ( row = gridVertical . row , column = gridVertical . column , sticky = Tkinter . W )
addEmptyRow ( gridVertical )
gridVertical . increment ( )
from fabmetheus_utilities . hidden_scrollbar import HiddenScrollbar
gridVertical . xScrollbar = HiddenScrollbar ( gridVertical . master , orient = Tkinter . HORIZONTAL )
gridVertical . xScrollbar . grid ( row = gridVertical . row + 1 , column = gridVertical . column , columnspan = 11 , sticky = Tkinter . E + Tkinter . W )
gridVertical . yScrollbar = HiddenScrollbar ( gridVertical . master )
gridVertical . yScrollbar . grid ( row = gridVertical . row , column = gridVertical . column + 12 , sticky = Tkinter . N + Tkinter . S )
canvasHeight = min ( 1000 , gridPosition . master . winfo_screenheight ( ) - 540 ) - 6 - int ( gridVertical . xScrollbar [ ' width ' ] )
canvasWidth = min ( 650 , gridPosition . master . winfo_screenwidth ( ) - 100 ) - 6 - int ( gridVertical . yScrollbar [ ' width ' ] )
gridVertical . canvas = Tkinter . Canvas ( gridVertical . master , height = canvasHeight , highlightthickness = 0 , width = canvasWidth )
gridVertical . frameGridVertical . master = Tkinter . Frame ( gridVertical . canvas )
for setting in gridVertical . repository . displayEntities :
setting . addToDialog ( gridVertical . frameGridVertical )
addEmptyRow ( gridVertical . frameGridVertical )
gridVertical . frameGridVertical . master . update_idletasks ( )
gridVertical . xScrollbar . config ( command = gridVertical . canvas . xview )
gridVertical . canvas [ ' xscrollcommand ' ] = gridVertical . xScrollbar . set
gridVertical . yScrollbar . config ( command = gridVertical . canvas . yview )
gridVertical . canvas [ ' yscrollcommand ' ] = gridVertical . yScrollbar . set
gridVertical . canvas . create_window ( 0 , 0 , anchor = Tkinter . NW , window = gridVertical . frameGridVertical . master )
gridVertical . canvas [ ' scrollregion ' ] = gridVertical . frameGridVertical . master . grid_bbox ( )
gridVertical . canvas . grid ( row = gridVertical . row , column = gridVertical . column , columnspan = 12 , sticky = Tkinter . E + Tkinter . W + Tkinter . N + Tkinter . S )
gridVertical . master . grid_rowconfigure ( gridVertical . row , weight = 1 )
gridVertical . master . grid_columnconfigure ( gridVertical . column + 11 , weight = 1 )
gridVertical . frameGridVertical . master . lift ( )
self . oldLatentString = self . latentStringVar . getString ( )
def focusSetMaster ( self , gridPosition ) :
" Set the focus to the plugin master. "
gridPosition . frameGridVertical . master . focus_set ( )
def getFromPath ( self , defaultRadioButton , directoryPath , repository ) :
" Initialize. "
self . defaultRadioButton = defaultRadioButton
self . directoryPath = directoryPath
self . name = ' PluginFrame '
self . repository = repository
repository . displayEntities . append ( self )
repository . preferences . append ( self )
return self
def setStateToValue ( self ) :
" Set the state of all the plugins to the value. "
for gridTableValue in self . gridTable . values ( ) :
cancelRepository ( gridTableValue . repository )
def setToDisplay ( self ) :
" Set the plugins to the display. "
pass
def update ( self ) :
" Update the frame. "
if len ( self . gridTable ) < 1 :
return
if self . oldLatentString == self . latentStringVar . getString ( ) :
return
self . oldLatentString = self . latentStringVar . getString ( )
self . repository . preferences . remove ( self )
for setting in self . repository . preferences :
setting . setToDisplay ( )
writeSettingsPrintMessage ( self . repository )
self . repository . preferences . append ( self )
if self . latentStringVar . getString ( ) in self . gridTable :
gridPosition = self . gridTable [ self . latentStringVar . getString ( ) ]
gridPosition . master . lift ( )
self . focusSetMaster ( gridPosition )
return
self . createFrame ( self . gridPosition )
def updateSaveListeners ( self ) :
" Update save listeners if any. "
gridTableKeys = self . gridTable . keys ( )
gridTableKeys . sort ( )
for gridTableKey in gridTableKeys :
saveRepository ( self . gridTable [ gridTableKey ] . repository )
def writeToRepositoryWriter ( self , repositoryWriter ) :
" Write tab separated name and value to the repository writer. "
pass
class PluginGroupFrame ( PluginFrame ) :
" A class to display the plugin groups in a frame. "
def createFrame ( self , gridPosition ) :
" Create the frame. "
gridVertical = GridVertical ( 0 , 0 )
gridVertical . master = Tkinter . LabelFrame ( gridPosition . master , borderwidth = 3 , relief = ' raised ' )
gridVertical . master . grid ( row = gridPosition . row , column = gridPosition . column , columnspan = 11 , sticky = Tkinter . E + Tkinter . W + Tkinter . N + Tkinter . S )
gridPosition . master . grid_rowconfigure ( gridPosition . row , weight = 1 )
gridPosition . master . grid_columnconfigure ( gridPosition . column + 10 , weight = 1 )
if self . latentStringVar . getString ( ) == ' ' :
self . defaultRadioButton . setSelect ( )
self . gridTable [ self . latentStringVar . getString ( ) ] = gridVertical
path = os . path . join ( self . directoryPath , self . latentStringVar . getString ( ) )
pluginModule = archive . getModuleWithPath ( path )
if pluginModule == None :
print ( ' this should never happen, pluginModule in addToDialog in PluginFrame in settings is None ' )
print ( path )
return
gridVertical . repository = getReadRepository ( pluginModule . getNewRepository ( ) )
gridVertical . setExecutablesRepository ( gridVertical . repository )
executeTitle = gridVertical . repository . executeTitle
2012-02-13 13:24:55 +00:00
#if executeTitle != None:
# executeButton = Tkinter.Button( gridVertical.master, activebackground = 'black', activeforeground = 'blue', text = executeTitle, command = gridVertical.execute )
# executeButton.grid( row = gridVertical.row, column = gridVertical.column, sticky = Tkinter.W )
# gridVertical.column += 1
#self.helpButton = Tkinter.Button( gridVertical.master, activebackground = 'black', activeforeground = 'white', text = "?", command = HelpPageRepository( gridVertical.repository ).openPage )
#self.helpButton.grid( row = gridVertical.row, column = gridVertical.column, sticky = Tkinter.W )
2012-02-10 16:20:03 +00:00
addEmptyRow ( gridVertical )
gridVertical . increment ( )
for setting in gridVertical . repository . displayEntities :
setting . addToDialog ( gridVertical )
gridVertical . master . update_idletasks ( )
gridVertical . master . lift ( )
self . oldLatentString = self . latentStringVar . getString ( )
def focusSetMaster ( self , gridPosition ) :
" Set the focus to the plugin master. "
gridPosition . master . focus_set ( )
class Radio ( BooleanSetting ) :
" A class to display, read & write a boolean with associated radio button. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
gridPosition . increment ( )
self . createRadioButton ( gridPosition )
self . radiobutton . grid ( row = gridPosition . row , column = 0 , columnspan = 3 , sticky = Tkinter . W )
self . setStateToValue ( )
def clickRadio ( self ) :
" Workaround for Tkinter bug, set the value. "
self . latentStringVar . setString ( self . radiobutton [ ' value ' ] )
if self . updateFunction != None :
self . updateFunction ( )
def createRadioButton ( self , gridPosition ) :
" Create the radio button. "
self . radiobutton = Tkinter . Radiobutton ( gridPosition . master , command = self . clickRadio , text = self . name , value = self . name , variable = self . latentStringVar . getVar ( ) )
LabelHelp ( self . repository . fileNameHelp , gridPosition . master , self . name , self . radiobutton )
def getFromRadio ( self , latentStringVar , name , repository , value ) :
" Initialize. "
self . getFromValueOnly ( name , repository , value )
self . latentStringVar = latentStringVar
repository . displayEntities . append ( self )
repository . preferences . append ( self )
#when addToMenu is added to this entity, the line below should be uncommented
# repository.menuEntities.append(self)
return self
def setSelect ( self ) :
" Set the int var and select the radio button. "
oldLatentStringValue = self . latentStringVar . getString ( )
self . latentStringVar . setString ( self . radiobutton [ ' value ' ] )
self . radiobutton . select ( )
if oldLatentStringValue == ' ' :
return False
return oldLatentStringValue != self . latentStringVar . getString ( )
def setStateToValue ( self ) :
" Set the checkbutton to the boolean. "
if self . value :
if self . setSelect ( ) :
if self . updateFunction != None :
self . updateFunction ( )
def setToDisplay ( self ) :
" Set the boolean to the checkbutton. "
self . value = ( self . latentStringVar . getString ( ) == self . radiobutton [ ' value ' ] )
class RadioCapitalized ( Radio ) :
" A class to display, read & write a boolean with associated radio button. "
def createRadioButton ( self , gridPosition ) :
" Create the radio button. "
capitalizedName = getEachWordCapitalized ( self . name )
self . radiobutton = Tkinter . Radiobutton ( gridPosition . master , command = self . clickRadio , text = capitalizedName , value = self . name , variable = self . latentStringVar . getVar ( ) )
class RadioCapitalizedButton ( Radio ) :
" A class to display, read & write a boolean with associated radio button. "
def createRadioButton ( self , gridPosition ) :
" Create the radio button. "
capitalizedName = getEachWordCapitalized ( self . name )
self . radiobutton = Tkinter . Radiobutton ( gridPosition . master , command = self . clickRadio , text = capitalizedName , value = self . name , variable = self . latentStringVar . getVar ( ) )
self . displayButton = Tkinter . Button ( gridPosition . master , activebackground = ' black ' , activeforeground = ' white ' , text = capitalizedName , command = self . displayDialog )
self . displayButton . grid ( row = gridPosition . row , column = 3 , columnspan = 2 )
def displayDialog ( self ) :
" Display function. "
ToolDialog ( ) . getFromPath ( self . path ) . display ( )
self . setSelect ( )
def getFromPath ( self , latentStringVar , name , path , repository , value ) :
" Initialize. "
self . getFromRadio ( latentStringVar , name , repository , value )
self . path = path
return self
class RadioPlugin ( RadioCapitalized ) :
" A class to display, read & write a boolean with associated radio button. "
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
self . createRadioButton ( gridPosition )
self . radiobutton [ ' activeforeground ' ] = ' magenta '
self . radiobutton [ ' selectcolor ' ] = ' white '
self . radiobutton [ ' borderwidth ' ] = 3
self . radiobutton [ ' indicatoron ' ] = 0
setButtonFontWeightString ( self . radiobutton , self . important )
self . incrementGridPosition ( gridPosition )
self . setStateToValue ( )
def getFromRadio ( self , important , latentStringVar , name , repository , value ) :
" Initialize. "
self . important = important
return RadioCapitalized . getFromRadio ( self , latentStringVar , name , repository , value )
def incrementGridPosition ( self , gridPosition ) :
" Increment the grid position. "
gridPosition . incrementGivenNumberOfColumns ( 10 )
self . radiobutton . grid ( row = gridPosition . row , column = gridPosition . column , sticky = Tkinter . W )
class TextSetting ( StringSetting ) :
" A class to display, read & write a text. "
def __init__ ( self ) :
" Set the update function to none. "
self . tokenConversions = [
TokenConversion ( ) ,
TokenConversion ( ' carriageReturn ' , ' \r ' ) ,
TokenConversion ( ' doubleQuote ' , ' " ' ) ,
TokenConversion ( ' newline ' , ' \n ' ) ,
TokenConversion ( ' semicolon ' , ' ; ' ) ,
TokenConversion ( ' singleQuote ' , " ' " ) ,
TokenConversion ( ' tab ' , ' \t ' ) ]
self . updateFunction = None
def addToDialog ( self , gridPosition ) :
" Add this to the dialog. "
gridPosition . increment ( )
self . label = Tkinter . Label ( gridPosition . master , text = self . name )
self . label . grid ( row = gridPosition . row , column = 0 , columnspan = 3 , sticky = Tkinter . W )
gridPosition . increment ( )
self . entry = Tkinter . Text ( gridPosition . master )
self . setStateToValue ( )
self . entry . grid ( row = gridPosition . row , column = 0 , columnspan = 5 , sticky = Tkinter . W )
LabelHelp ( self . repository . fileNameHelp , gridPosition . master , self . name , self . label )
def getFromValue ( self , name , repository , value ) :
" Initialize. "
self . getFromValueOnly ( name , repository , value )
repository . displayEntities . append ( self )
repository . preferences . append ( self )
return self
def setStateToValue ( self ) :
" Set the entry to the value. "
try :
self . entry . delete ( 1.0 , Tkinter . END )
self . entry . insert ( Tkinter . INSERT , self . value )
except :
pass
def setToDisplay ( self ) :
" Set the string to the entry field. "
valueString = self . entry . get ( 1.0 , Tkinter . END )
self . setValueToString ( valueString )
def setValueToSplitLine ( self , lineIndex , lines , splitLine ) :
" Set the value to the second word of a split line. "
replacedValue = splitLine [ 1 ]
for tokenConversion in reversed ( self . tokenConversions ) :
replacedValue = tokenConversion . getTokenizedString ( replacedValue )
self . setValueToString ( replacedValue )
def writeToRepositoryWriter ( self , repositoryWriter ) :
" Write tab separated name and value to the repository writer. "
replacedValue = self . value
for tokenConversion in self . tokenConversions :
replacedValue = tokenConversion . getNamedString ( replacedValue )
repositoryWriter . write ( ' %s %s %s \n ' % ( self . name , globalSpreadsheetSeparator , replacedValue ) )
class TokenConversion :
" A class to convert tokens in a string. "
def __init__ ( self , name = ' replaceToken ' , token = ' ___replaced___ ' ) :
" Set the name and token. "
self . replacedName = ' ___replaced___ ' + name
self . token = token
def getNamedString ( self , text ) :
" Get a string with the tokens changed to names. "
return text . replace ( self . token , self . replacedName )
def getTokenizedString ( self , text ) :
" Get a string with the names changed to tokens. "
return text . replace ( self . replacedName , self . token )
class ToolDialog :
" A class to display the tool repository dialog. "
def addPluginToMenu ( self , menu , path ) :
" Add the display command to the menu. "
name = os . path . basename ( path )
self . path = path
menu . add_command ( label = getEachWordCapitalized ( name ) + ' ... ' , command = self . display )
def display ( self ) :
" Display the tool repository dialog. "
global globalRepositoryDialogListTable
for repositoryDialog in globalRepositoryDialogListTable :
if getPathInFabmetheusFromFileNameHelp ( repositoryDialog . repository . fileNameHelp ) == self . path :
liftRepositoryDialogs ( globalRepositoryDialogListTable [ repositoryDialog ] )
return
self . repositoryDialog = getDisplayedDialogFromPath ( self . path )
def getFromPath ( self , path ) :
" Initialize and return display function. "
self . path = path
return self
class WindowPosition ( StringSetting ) :
" A class to display, read & write a window position. "
def addToDialog ( self , gridPosition ) :
" Set the root to later get the geometry. "
self . root = gridPosition . master
self . setToDisplay ( )
def getFromValue ( self , repository , value ) :
" Initialize. "
self . getFromValueOnly ( ' WindowPosition ' , repository , value )
repository . displayEntities . append ( self )
repository . preferences . append ( self )
return self
def setToDisplay ( self ) :
" Set the string to the window position. "
try :
geometryString = self . root . geometry ( )
except :
return
if geometryString == ' 1x1+0+0 ' :
return
firstPlusIndexPlusOne = geometryString . find ( ' + ' ) + 1
self . value = geometryString [ firstPlusIndexPlusOne : ]
def setWindowPosition ( self ) :
" Set the window position. "
movedGeometryString = ' %s x %s + %s ' % ( self . root . winfo_reqwidth ( ) , self . root . winfo_reqheight ( ) , self . value )
self . root . geometry ( movedGeometryString )
class RepositoryDialog :
def __init__ ( self , repository , root ) :
" Add entities to the dialog. "
self . isFirst = ( len ( globalRepositoryDialogListTable . keys ( ) ) == 0 )
self . closeListener = CloseListener ( self )
self . repository = repository
self . gridPosition = GridVertical ( 0 , - 1 )
self . gridPosition . setExecutablesRepository ( repository )
self . gridPosition . master = root
self . root = root
self . openDialogListeners = [ ]
repository . repositoryDialog = self
root . withdraw ( )
title = repository . title
if repository . fileNameInput != None :
title = os . path . basename ( repository . fileNameInput . value ) + ' - ' + title
root . title ( title )
fileHelpMenuBar = FileHelpMenuBar ( root )
fileHelpMenuBar . completeMenu ( self . close , repository , self . save , self )
for setting in repository . displayEntities :
setting . addToDialog ( self . gridPosition )
if self . gridPosition . row < 20 :
addEmptyRow ( self . gridPosition )
self . addButtons ( repository , root )
root . update_idletasks ( )
self . setWindowPositionDeiconify ( )
root . deiconify ( )
for openDialogListener in self . openDialogListeners :
openDialogListener . openDialog ( )
def __repr__ ( self ) :
" Get the string representation of this RepositoryDialog. "
return self . repository . title
def addButtons ( self , repository , root ) :
" Add buttons to the dialog. "
columnIndex = 0
self . gridPosition . increment ( )
saveCommand = self . save
saveText = ' Save '
if self . isFirst :
saveCommand = saveAll
saveText = ' Save All '
if repository . executeTitle != None :
executeButton = Tkinter . Button ( root , activebackground = ' black ' , activeforeground = ' blue ' , text = repository . executeTitle , command = self . gridPosition . execute )
executeButton . grid ( row = self . gridPosition . row , column = columnIndex , columnspan = 2 , sticky = Tkinter . W )
columnIndex + = 2
self . helpButton = Tkinter . Button ( root , activebackground = ' black ' , activeforeground = ' white ' , text = " ? " , command = HelpPageRepository ( self . repository ) . openPage )
self . helpButton . grid ( row = self . gridPosition . row , column = columnIndex , sticky = Tkinter . W )
self . closeListener . listenToWidget ( self . helpButton )
columnIndex + = 6
cancelButton = Tkinter . Button ( root , activebackground = ' black ' , activeforeground = ' orange ' , command = self . cancel , fg = ' orange ' , text = ' Cancel ' )
cancelButton . grid ( row = self . gridPosition . row , column = columnIndex )
columnIndex + = 1
self . saveButton = Tkinter . Button ( root , activebackground = ' black ' , activeforeground = ' darkgreen ' , command = saveCommand , fg = ' darkgreen ' , text = saveText )
self . saveButton . grid ( row = self . gridPosition . row , column = columnIndex )
def cancel ( self , event = None ) :
" Set all entities to their saved state. "
cancelRepository ( self . repository )
def close ( self , event = None ) :
" The dialog was closed. "
try :
self . root . destroy ( )
except :
pass
def save ( self , event = None ) :
" Set the entities to the dialog then write them. "
saveRepository ( self . repository )
def setWindowPositionDeiconify ( self ) :
" Set the window position if that setting exists. "
for setting in self . repository . preferences :
if setting . name == ' WindowPosition ' :
setting . setWindowPosition ( )
return