513
537
def setup_menu(self, truncate, minmax, inplace, collvalue):
514
538
"""Setup context menu"""
539
self.empty_ws_menu = QMenu(self)
540
self.paste_action = create_action(self,
541
translate("DictEditor", "Paste"),
542
icon=get_icon('editpaste.png'),
543
triggered=self.paste)
544
self.empty_ws_menu.addAction(self.paste_action)
546
self.copy_action = create_action(self,
547
translate("DictEditor", "Copy"),
548
icon=get_icon('editcopy.png'),
515
550
self.edit_action = create_action(self,
516
551
translate("DictEditor", "Edit"),
517
552
icon=get_icon('edit.png'),
573
608
triggered=self.duplicate_item)
574
609
menu = QMenu(self)
575
610
menu_actions = [self.edit_action, self.plot_action, self.imshow_action,
576
self.save_array_action,
577
self.insert_action, self.remove_action, None,
578
self.rename_action,self.duplicate_action, None,
579
self.truncate_action, self.inplace_action,
611
self.save_array_action, self.insert_action,
612
self.remove_action, self.copy_action, self.paste_action,
613
None, self.rename_action,self.duplicate_action,
614
None, self.truncate_action, self.inplace_action,
580
615
self.collvalue_action]
581
616
if ndarray is not FakeObject:
582
617
menu_actions.append(self.minmax_action)
689
728
for index in indexes:
690
729
if not index.isValid():
731
one = translate("DictEditor", "Do you want to remove selected item?")
732
more = translate("DictEditor",
733
"Do you want to remove all selected items?")
692
734
answer = QMessageBox.question(self,
693
translate("DictEditor", "Remove"),
694
translate("DictEditor", "Do you want to remove selected item%1?") \
695
.arg('s' if len(indexes)>1 else ''),
696
QMessageBox.Yes | QMessageBox.No)
735
translate("DictEditor", "Remove"),
736
one if len(indexes) == 1 else more,
737
QMessageBox.Yes | QMessageBox.No)
697
738
if answer == QMessageBox.Yes:
698
739
idx_rows = unsorted_unique(map(lambda idx: idx.row(), indexes))
699
740
keys = [ self.model.keys[idx_row] for idx_row in idx_rows ]
772
814
index = self.currentIndex()
773
815
if self.__prepare_plot():
774
from pylab import plot, show
817
import guiqwt.pyplot as plt
819
import matplotlib.pyplot as plt
775
820
data = self.delegate.get_value(index)
825
except ValueError, error:
826
QMessageBox.critical(self, translate("DictEditor", "Plot"),
827
translate("DictEditor", "<b>Unable to plot data.</b>"
828
"<br><br>Error message:<br>%1").arg(str(error)))
779
830
def imshow_item(self):
780
831
"""Imshow item"""
781
832
index = self.currentIndex()
782
833
if self.__prepare_plot():
783
from pylab import imshow, show
835
import guiqwt.pyplot as plt
837
import matplotlib.pyplot as plt
784
838
data = self.delegate.get_value(index)
843
except ValueError, error:
844
QMessageBox.critical(self, translate("DictEditor", "Plot"),
845
translate("DictEditor", "<b>Unable to show image.</b>"
846
"<br><br>Error message:<br>%1").arg(str(error)))
788
848
def save_array(self):
804
864
QMessageBox.critical(self, title,
805
865
translate('DictEditor', "<b>Unable to save array</b>"
806
866
"<br><br>Error message:<br>%1").arg(str(error)))
809
class DictEditorTableView(BaseTableView):
810
"""DictEditor table view"""
811
def __init__(self, parent, data, readonly=False, title="",
812
names=False, truncate=True, minmax=False,
813
inplace=False, collvalue=True):
814
BaseTableView.__init__(self, parent)
815
self.dictfilter = None
816
self.readonly = readonly or isinstance(data, tuple)
819
DictModelClass = ReadOnlyDictModel if self.readonly else DictModel
820
self.model = DictModelClass(self, data, title, names=names,
821
truncate=truncate, minmax=minmax,
823
self.setModel(self.model)
824
self.delegate = DictDelegate(self, inplace=inplace)
825
self.setItemDelegate(self.delegate)
828
self.menu = self.setup_menu(truncate, minmax, inplace, collvalue)
829
self.copy_action = create_action(self,
830
translate("DictEditor", "Copy"),
831
icon=get_icon('editcopy.png'),
833
self.paste_action = create_action(self,
834
translate("DictEditor", "Paste"),
835
icon=get_icon('editpaste.png'),
836
triggered=self.paste)
837
self.menu.insertAction(self.remove_action, self.copy_action)
838
self.menu.insertAction(self.remove_action, self.paste_action)
840
self.empty_ws_menu = QMenu(self)
841
self.empty_ws_menu.addAction(self.paste_action)
843
def remove_values(self, keys):
845
Remove values from data
846
(implemented differently for remote table view)
848
data = self.model.get_data()
849
for key in sorted(keys,reverse=True):
853
def copy_value(self, orig_key, new_key):
856
(implemented differently for remote table view)
858
data = self.model.get_data()
859
data[new_key] = data[orig_key]
862
def new_value(self, key, value):
864
Create new value in data
865
(implemented differently for remote table view)
867
data = self.model.get_data()
871
def refresh_menu(self):
872
"""Refresh context menu"""
873
data = self.model.get_data()
874
index = self.currentIndex()
875
condition = (not isinstance(data, tuple)) and index.isValid() \
876
and not self.readonly
877
self.edit_action.setEnabled( condition )
878
self.remove_action.setEnabled( condition )
879
self.insert_action.setEnabled( not self.readonly )
880
self.refresh_plot_entries(index)
882
def set_filter(self, dictfilter=None):
883
"""Set table dict filter"""
884
self.dictfilter = dictfilter
887
868
"""Copy text to clipboard"""
888
869
clipboard = QApplication.clipboard()
889
data = self.model.get_data()
891
871
for idx in self.selectedIndexes():
892
872
if not idx.isValid:
895
if isinstance(data,dict):
896
_txt = unicode(data.get(self.model.keys[idx.row()]))
898
_txt = unicode(data[idx.row()])
874
clipl.append(unicode(self.delegate.get_value(idx)))
900
875
clipboard.setText(u'\n'.join(clipl))
902
877
def import_from_string(self, text, title=None):
903
878
"""Import data from string"""
904
# if isinstance(text, basestring):
905
# text = QString(text)
906
879
data = self.model.get_data()
907
varname_base = translate("DictEditor", "new")
909
varname_base = str(varname_base)
910
except UnicodeEncodeError:
911
varname_base = unicode(varname_base)
912
get_varname = lambda index: varname_base + ("%03d" % index)
914
while get_varname(index) in data:
916
880
editor = ImportWizard(self, text, title=title,
917
881
contents_title=translate("DictEditor",
918
882
"Clipboard contents"),
919
varname=get_varname(index))
883
varname=fix_reference_name("data",
884
blacklist=data.keys()))
920
885
if editor.exec_():
921
886
var_name, clip_data = editor.get_data()
922
data[var_name] = clip_data
887
self.new_value(var_name, clip_data)
926
890
"""Import text/data/code from clipboard"""
937
901
translate("DictEditor", "Empty clipboard"),
938
902
translate("DictEditor", "Nothing to be imported"
939
903
" from clipboard."))
906
class DictEditorTableView(BaseTableView):
907
"""DictEditor table view"""
908
def __init__(self, parent, data, readonly=False, title="",
909
names=False, truncate=True, minmax=False,
910
inplace=False, collvalue=True):
911
BaseTableView.__init__(self, parent)
912
self.dictfilter = None
913
self.readonly = readonly or isinstance(data, tuple)
916
DictModelClass = ReadOnlyDictModel if self.readonly else DictModel
917
self.model = DictModelClass(self, data, title, names=names,
918
truncate=truncate, minmax=minmax,
920
self.setModel(self.model)
921
self.delegate = DictDelegate(self, inplace=inplace)
922
self.setItemDelegate(self.delegate)
925
self.menu = self.setup_menu(truncate, minmax, inplace, collvalue)
927
def remove_values(self, keys):
929
Remove values from data
930
(implemented differently for remote table view)
932
data = self.model.get_data()
933
for key in sorted(keys,reverse=True):
937
def copy_value(self, orig_key, new_key):
940
(implemented differently for remote table view)
942
data = self.model.get_data()
943
data[new_key] = data[orig_key]
946
def new_value(self, key, value):
948
Create new value in data
949
(implemented differently for remote table view)
951
data = self.model.get_data()
955
def refresh_menu(self):
956
"""Refresh context menu"""
957
data = self.model.get_data()
958
index = self.currentIndex()
959
condition = (not isinstance(data, tuple)) and index.isValid() \
960
and not self.readonly
961
self.edit_action.setEnabled( condition )
962
self.remove_action.setEnabled( condition )
963
self.insert_action.setEnabled( not self.readonly )
964
self.refresh_plot_entries(index)
966
def set_filter(self, dictfilter=None):
967
"""Set table dict filter"""
968
self.dictfilter = dictfilter
942
971
class DictEditorWidget(QWidget):
1100
1132
return output_dict
1103
if __name__ == "__main__":
1135
def get_test_data():
1136
"""Create test data"""
1137
import numpy as np, PIL.Image
1138
image = PIL.Image.fromarray(np.random.rand(100, 100))
1105
1139
testdict = {'d': 1, 'a': np.random.rand(10, 10), 'b': [1, 2]}
1106
1140
testdate = datetime.date(1945, 5, 8)
1107
example = {'str': 'kjkj kj k j j kj k jkj',
1109
'list': [1, 3, [4, 5, 6], 'kjkj', None],
1110
'tuple': ([1, testdate, testdict], 'kjkj', None),
1113
'array': np.random.rand(10, 10),
1114
'empty_array': np.array([]),
1116
'datetime': datetime.datetime(1945, 5, 8),
1119
# # Remote dict test:
1120
# from spyderlib.widgets.monitor import make_remote_view
1121
# remote = make_remote_view(example)
1122
# from pprint import pprint
1124
# if QApplication.startingUp():
1126
# dialog = DictEditor(remote, remote=True)
1127
# if dialog.exec_():
1128
# print dialog.get_copy()
1130
out = dedit(example)
1141
return {'str': 'kjkj kj k j j kj k jkj',
1143
'list': [1, 3, [4, 5, 6], 'kjkj', None],
1144
'tuple': ([1, testdate, testdict], 'kjkj', None),
1147
'array': np.random.rand(10, 10),
1148
'1D-array': np.linspace(-10, 10),
1149
'empty_array': np.array([]),
1152
'datetime': datetime.datetime(1945, 5, 8),
1156
"""Dictionary editor test"""
1157
out = dedit( get_test_data() )
1131
1158
print "out:", out
b'\\ No newline at end of file'
1160
def remote_editor_test():
1161
"""Remote dictionary editor test"""
1162
from spyderlib.widgets.externalshell.globalsexplorer import get_settings
1163
from spyderlib.widgets.externalshell.monitor import make_remote_view
1164
remote = make_remote_view(get_test_data(), get_settings())
1165
from pprint import pprint
1167
_app = qapplication()
1168
dialog = DictEditor(remote, remote=True)
1170
print dialog.get_copy()
1172
if __name__ == "__main__":