gpt4 book ai didi

python - 在 urwid 中使用列表框时出现“AttributeError”

转载 作者:行者123 更新时间:2023-12-01 05:39:29 28 4
gpt4 key购买 nike

下面使用 urwid 库的代码应该在控制台屏幕上显示 yml 文件的内容(如给定 here )(按照此处的 Application Form 布局:

代码是:

import sys
sys.path.append('./lib')
import os
from pprint import pprint
import random
import urwid
ui = urwid.raw_display.Screen()
pile = urwid.Pile([])
from collections import OrderedDict
import yaml_ordered_dict
import collections
import yaml

import itertools

import copy

class FormDisplay(object):

def __init__(self):
global ui
#self.ui = urwid.raw_display.Screen()
self.ui = ui
self.palette = self.ui.register_palette([
('Field', 'dark green, bold', 'black'), # information fields, Search: etc.
('Info', 'dark green', 'black'), # information in fields
('Bg', 'black', 'black'), # screen background
('InfoFooterText', 'white', 'dark blue'), # footer text
('InfoFooterHotkey', 'dark cyan, bold', 'dark blue'), # hotkeys in footer text
('InfoFooter', 'black', 'dark blue'), # footer background
('InfoHeaderText', 'white, bold', 'dark blue'), # header text
('InfoHeader', 'black', 'dark blue'), # header background
('BigText', RandomColor(), 'black'), # main menu banner text
('GeneralInfo', 'brown', 'black'), # main menu text
('LastModifiedField', 'dark cyan, bold', 'black'), # Last modified:
('LastModifiedDate', 'dark cyan', 'black'), # info in Last modified:
('PopupMessageText', 'black', 'dark cyan'), # popup message text
('PopupMessageBg', 'black', 'dark cyan'), # popup message background
('SearchBoxHeaderText', 'light gray, bold', 'dark cyan'), # field names in the search box
('SearchBoxHeaderBg', 'black', 'dark cyan'), # field name background in the search box
('OnFocusBg', 'white', 'dark magenta') # background when a widget is focused
])
urwid.set_encoding('utf8')

def main(self):
global ui
#self.view = ui.run_wrapper(formLayout)
#urwid initialisation first or yml readin first. i chose yml reading
yOrDict = yaml_ordered_dict.load('ApplyForm.yml')
yOrDictLevel1 = yOrDict.get('ApplyForm')
self.ui.start()
self.view = formLayout(yOrDictLevel1)

self.loop = urwid.MainLoop(self.view, self.palette)
self.loop.widget = self.view
self.loop.run()

def find_value(needle, container):
# Already found the object. Return.
if isinstance(container, basestring) and needle in container:
return True

values = None
if isinstance(container, dict):
values = container.values()
elif hasattr(container, '__iter__'):
values = container.__iter__()

if values is None:
return False

# Check deeper in the container, if needed.
for val in values:
if find_value(needle, val):
return True

# No match found.
return False

def getChildMap(tmpMap):
tMap = tmpMap
tmpLen = len(tMap)
listOfKeys = tMap.keys()
topKey = listOfKeys[0]
#print('topkey', topKey)
mapObtained = tMap.get(topKey)

#print('getChildMap',mapObtained)
return mapObtained

def getMapForKeyIndex(tmpMap,index):
listOfKeysForMap = tmpMap.keys()
i = index
mapObtained = collections.OrderedDict(itertools.islice(tmpMap.items(), i, i+1))
#print(type(mapObtained))
#print("getMapForKeyIndex: key and map",i,mapObtained)
return mapObtained

def checkValOfKey(key,tmpMap):
tMap = tmpMap

for k, v in tMap.items():
if k == key :
tVal = tMap[key]

#print('checkValOfKey:tVal',tVal)
return tVal

def removeTopItem(tmpMap):
tMap = tmpMap
listOfKeys = tMap.keys()
topKey = listOfKeys[0]
del tMap[topKey]
return tMap

def createBlock(mapToWorkWith) :
global pile
#pile = urwid.Pile([])


tmapToWorkWith = copy.deepcopy(mapToWorkWith)
tmapToWorkWith = getChildMap(tmapToWorkWith)
#print('createBlock: tmapToWorkWith', tmapToWorkWith)
reducedMapToCarry = copy.deepcopy(tmapToWorkWith)

listOfKeys = tmapToWorkWith.keys()

#if blockPresentAsValueInMap(tmapToWorkWith) == True :
if checkValOfKey('$type',tmapToWorkWith) == 'Block' :
#create a block nd pile
print('XXXXXXXXcreate block and pile listXXXXXXXX')
#pile = urwid.Pile([])
keytoBeginPile = 2
#if displayPresentAsKeyInMap(tmapToWorkWith) == True :
#if checkContainmentOfKeyInMap('$display',(tmapToWorkWith)) :
reducedMapToCarry = removeTopItem(reducedMapToCarry)
reducedMapToCarry = removeTopItem(reducedMapToCarry)

if (tmapToWorkWith.has_key('$display')) == True :
print('display value ',tmapToWorkWith['$display'])
displayText = tmapToWorkWith['$display']
text = urwid.Text(('GeneralInfo', displayText),
align='center')
pile.contents.append(text)


keytoBeginPile +=1
#addDisplayToPile
reducedMapToCarry = removeTopItem(reducedMapToCarry)


for k in range(keytoBeginPile,len(tmapToWorkWith)) :
#//get the value of key at indexkeytoBeginPile in tmapToWorkWith
tmpMap = tmapToWorkWith.get(listOfKeys[k])
if checkValOfKey('$type',tmpMap) != 'Block' :
print('##add to Pile##')
print('display value ',tmpMap['$display'])
displayText = tmpMap['$display']
text = urwid.Text(('GeneralInfo', displayText),
align='center')
#pile.contents.append(text,options='pack')
pile.append(text)
keytoBeginPile +=1
reducedMapToCarry = removeTopItem(reducedMapToCarry)
#print('for Loop traversal: map', reducedMapToCarry)
#mapToPass(pop)
continue
else :
createBlock(reducedMapToCarry)

#return urwid.LineBox(urwid.AttrWrap(urwid.Overlay(urwid.LineBox(urwid.Padding(
# pile, align='center', left=3, right=3)), Banner, 'center', 150, 'middle', None),
# 'GeneralInfo'))

def formLayout(topMap):
global ui
global pile

f3 = open('OrderedMapInFinalApp.yaml',"w")
newMap = topMap #check if needed at all
yaml.dump(newMap, f3)


content = urwid.SimpleListWalker([])
listbox = urwid.ListBox(content)

#orderedMap has come
#read the key value and start for loop
print('lenght of map',len(newMap))
for i in range(len(newMap)):
mapToWorkWith = getMapForKeyIndex(newMap,i)
#print('for loop i nd mapToWorkWith Is',i,mapToWorkWith)

if i == 0 :
if (checkValOfKey('$type',mapToWorkWith) == 'Block') :
print('1st key read')
continue

else :
if (mapToWorkWith.has_key('TITLE') == True):
print('2nd key read')
continue

else :
pile = ([])
createBlock(mapToWorkWith)
#content.append(addBlockToOverallLayout())
content.append(pile)
continue
fill = urwid.Filler(listbox)

frame = urwid.Frame(fill,header=urwid.Pile([textT,textSH]),footer=textF)

dim = ui.get_cols_rows()
#ui is treated as global handle for all functions, either belonging
#to any class or standalone functions such as formLayout
#need to check if screen has been started
if not ui._started:
print("Screen has not been started, so no use of rendering.Thus return :-( ")
return
#ui.draw_screen(dim, listbox.render(dim, True))
return frame
#return listbox

def RandomColor():
'''Pick a random color for the main menu text'''
listOfColors = ['dark red', 'dark green', 'brown', 'dark blue',
'dark magenta', 'dark cyan', 'light gray',
'dark gray', 'light red', 'light green', 'yellow',
'light blue', 'light magenta', 'light cyan', 'default']
color = listOfColors[random.randint(0, 14)]
return color

def main():
#global ui
form = FormDisplay()
form.main()

########################################
##### MAIN ENTRY POINT
########################################
if __name__ == '__main__':
main()

#

代码使用ui来表示控制台屏幕。我使用了一个全局列表框 api,它将包含 yml 文件中的值,其键是 $display。代码失败并给出以下错误:

Traceback (most recent call last):  
File "./yamlUrwidUIPhase8FrameFinalAppC.py", line 308, in <module>
main()
File "./yamlUrwidUIPhase8FrameFinalAppC.py", line 302, in main
form.main()
File "./yamlUrwidUIPhase8FrameFinalAppC.py", line 61, in main
self.loop.run()
File "/home/gehna/urwidWorkInProgress/urwid/main_loop.py", line 272, in run
self.screen.run_wrapper(self._run)
File "/home/gehna/urwidWorkInProgress/urwid/raw_display.py", line 242, in run_wrapper
return fn()
File "/home/gehna/urwidWorkInProgress/urwid/main_loop.py", line 312, in _run
self.draw_screen()
File "/home/gehna/urwidWorkInProgress/urwid/main_loop.py", line 563, in draw_screen
canvas = self._topmost_widget.render(self.screen_size, focus=True)
File "/home/gehna/urwidWorkInProgress/urwid/widget.py", line 141, in cached_render
canv = fn(self, size, focus=focus)
File "/home/gehna/urwidWorkInProgress/urwid/container.py", line 1058, in render
focus and self.focus_part == 'body')
File "/home/gehna/urwidWorkInProgress/urwid/widget.py", line 141, in cached_render
canv = fn(self, size, focus=focus)
File "/home/gehna/urwidWorkInProgress/urwid/decoration.py", line 811, in render
top, bottom = self.filler_values(size, focus)
File "/home/gehna/urwidWorkInProgress/urwid/decoration.py", line 796, in filler_values
height = self._original_widget.rows((maxcol,),focus=focus)
AttributeError: 'ListBox' object has no attribute 'rows'

我使用 ddd 和 pydb 调试器检查了代码的解析部分,解析 yml 部分似乎没问题,并且 print 语句正确给出了 $display 的值。我使用 ui 的方式有问题吗?我应该使用draw_screen 来代替吗?

最佳答案

我在尝试输入 QuestionBox tutorial example 时遇到了同样的错误在列表框中。这个answer帮我解决了。

import urwid

def exit_on_q(key):
if key in ('q', 'Q'):
raise urwid.ExitMainLoop()

class QuestionBox(urwid.Filler):
def keypress(self, size, key):
if key != 'enter':
return super(QuestionBox, self).keypress(size, key)
self.original_widget = urwid.Text(
u"Nice to meet you,\n%s.\n\nPress Q to exit." %
edit.edit_text)

edit = urwid.Edit(u"What is your name?\n")
fill = urwid.BoxAdapter(QuestionBox(edit), height=2)
lb = urwid.ListBox([fill])
loop = urwid.MainLoop(lb, unhandled_input=exit_on_q)
loop.run()

关于python - 在 urwid 中使用列表框时出现“AttributeError”,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17978497/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com