Russian Qt Forum
Ноябрь 25, 2024, 14:07 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1]   Вниз
  Печать  
Автор Тема: Сохранение и открытие QTableWidget  (Прочитано 9008 раз)
Dr.robot
Гость
« : Январь 29, 2017, 15:37 »

Здравствуйте.
У меня вот такой вопрос, как сохранить таблицу со всем ее содержимым (иконки, картинки, чекбоксы итд...)
Я смог сохранять таблицу с содержанием текста все работает, но когда я вставляю картинки то их по началу вообще не сохраняло.
Потом я узнал что надо задать роль для картинки, задал но теперь я сохраняю в ячейке PyQt4.QtGui.QTableWidgetItem object at 0x0000000003DC2EE8
это объект памяти. Собственно как сохранить в таблице не только текст.
Вот код урезаный что бы влез
Код
Python
import sys
from PyQt4.QtCore import *
from PyQt4.QtGui import *
from functools import partial
import xlwt
import xlrd
 
class My_Widget(QWidget):
   def __init__(self, parent=None):
       QWidget.__init__(self, parent)
       self.table = QTableWidget(self)
       self.table.setRowCount(20)
       self.table.setColumnCount(20)
       self.table.setGeometry(0, 29, 1600, 1600)
       self.table.show()
       self.table.horizontalHeader().hide()
       self.table.verticalHeader().hide()
       self.table.setColumnWidth(0, 30)
       self.table.setRowHeight(0, 30)
       self.table.resizeColumnsToContents()
       delegate = MyDelegate()
       self.table.setItemDelegate(delegate)
       #Цвет таблицы и стиль
       self.table.setStyleSheet("gridline-color: #FFC0CB")
       self.table.setGridStyle(1)
       self.table.setFrameStyle(QFrame.NoFrame)
 
#---------------------------------------------
       self.setGeometry(300, 300, 800, 600)
       self.setWindowTitle('icon')
#---------------------------------------------
       self.lay = QHBoxLayout()
       self.lay.setAlignment(Qt.AlignLeft | Qt.AlignTop)
       self.lay.setMargin(0)
       self.lay.setSpacing(0)
       self.setLayout(self.lay)
       self.BUTTNS = [
           {'text': u'', 'img': 'sym1.png', 'ico': 'sym1.png'},
           {'text': u'', 'img': 'sym2.png', 'ico': 'sym2.png'}]
#---------------------------------------------
       for i in self.BUTTNS:
           i["btn"] = QPushButton(i["text"])
           i["btn"].setIcon(QIcon(i["ico"]))
           i["btn"].clicked.connect(partial(self.on_clicked_btn, QPixmap(i["img"])))
           self.lay.addWidget(i["btn"])
#---------------------------------------------
       self.btn = QPushButton("save xls", self)
       self.btn.setGeometry(75, 0, 80, 30)
       self.btn.sizeHint()
       self.connect(self.btn, SIGNAL("clicked()"), self.save_file)
       self.btn2 = QPushButton("open xls", self)
       self.btn2.setGeometry(150, 0, 80, 30)
       self.btn2.sizeHint()
       self.connect(self.btn2, SIGNAL("clicked()"), self.open_file)
#---------------------------------------------
 
 
   def on_clicked_btn(self, img):
       item = QTableWidgetItem()
       item.setData(Qt.DecorationRole, img)
       self.table.setItem(self.table.currentRow(), self.table.currentColumn(), item)
 
 
#---------------------------------------------
 
#--------------------------------------------
   def save_file(self):
       filename = (QFileDialog.getSaveFileName(self, 'Сохранить', '', ".xls(*.xls)"))
       wbk = xlwt.Workbook()
       sheet = wbk.add_sheet("схема", cell_overwrite_ok=True)
       self.s_f(sheet)
       wbk.save(filename)
 
   def s_f(self, sheet):
       for currentColumn in range(self.table.columnCount()):
           for currentRow in range(self.table.rowCount()):
 
               my_icon = self.table.item(currentRow, currentColumn)
               sheet.write(currentRow, currentColumn, str(my_icon or ''))
 
#-------------------------------------------
 
   def open_file(self):
       filename = QFileDialog.getOpenFileName(self, 'Открыть', '', '.xls(*.xls)')
 
       book = xlrd.open_workbook(filename)
       sheet = book.sheet_by_index(0)
       data = [[sheet.cell_value(r, c)for c in range(sheet.ncols)]for r in range(sheet.nrows)]
 
       for row, columnvalues in enumerate(data):
           for column, value in enumerate(columnvalues):
               item = QTableWidgetItem()
               item.setData(Qt.DisplayRole, str(value))
               self.table.setItem(row, column, item)
 
#--------------------Делегат для ячейки
class MyDelegate(QStyledItemDelegate):
   def paint(self, painter, option, index):
       img = index.model().data(index, Qt.DecorationRole)
       if img is None:
           super().paint(painter, option, index)
           return
 
       rect = option.rect
       w, h = rect.size().width(), rect.size().height()
       img = img.scaled(w, h, Qt.KeepAspectRatio, Qt.SmoothTransformation)
 
       painter.drawPixmap(rect, img)
 
       item_option = QStyleOptionViewItem(option)
       self.initStyleOption(item_option, index)
       #Для полупрозрачности выделения
       if item_option.state & QStyle.State_Selected:
           color = item_option.palette.color(QPalette.Highlight)
           color.setAlpha(180)
 
           painter.save()
           painter.setPen(Qt.NoPen)
           painter.setBrush(color)
           painter.drawRect(rect)
           painter.restore()
           # super().paint(painter, option, index)
 
#--------------
if __name__ == '__main__':
 app = QApplication(sys.argv)
 widget = My_Widget()
 widget.show()
 sys.exit(app.exec_())

Может не так вставляю картинку а может не так сохраняю или и то и другое.
Или может есть другой способ сохранения ?
« Последнее редактирование: Январь 29, 2017, 15:42 от Dr.robot » Записан
gil9red
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 1805



Просмотр профиля WWW
« Ответ #1 : Январь 30, 2017, 08:53 »

Используйте у QTableWidgetItem метод/свойство для получения его текста, а str(my_icon or '') вам точно не поможет

Мне кажется, вам сначала нужно проверить что та либа для создания excel-файлов умеет сохранять картинки в ячейках
Записан

Dr.robot
Гость
« Ответ #2 : Январь 30, 2017, 18:07 »

Да ты прав xlwt может сохранять только bmp картинки но я попробовал и у меня программа зависла,
а так bmp картинки вставляются:
Код
Python
sheet.insert_bitmap("sym1.bmp",1,1)
работает но зависает когда делаю вот так
Код
Python
sheet.insert_bitmap(currentRow, currentColumn, my_icon)
сейчас попробую с xlsxwriter
Записан
gil9red
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 1805



Просмотр профиля WWW
« Ответ #3 : Январь 30, 2017, 18:20 »

т.е. sheet.insert_bitmap("sym1.bmp",1,1) берет файл sym1.bmp, который лежит в папке с скриптом и вставляет в первую ячейку первой строки?

Да ты прав xlwt может сохранять только bmp картинки но я попробовал и у меня программа зависла,
а так bmp картинки вставляются:
Код
Python
sheet.insert_bitmap("sym1.bmp",1,1)
работает но зависает когда делаю вот так
Код
Python
sheet.insert_bitmap(currentRow, currentColumn, my_icon)

странный порядок аргументов в insert_bitmap, my_icon по идеи должна быть в первом аргументе

Предлагаю следующее: получаете ячейку QTableWidgetItem, у нее берете иконку, сохраняете ее как bmp и в insert_bitmap передаете ее путь после удаляете ее, что-то вроде такого:

Код
Python
icon_file_name = "cell_icon.bmp"
 
#
# Тут начало цикла для перебора ячеек
#
 
item = self.table.item(currentRow, currentColumn)
 
# Сохранение иконки ячейки в файл
img = item.data(Qt.DecorationRole)
img.save(icon_file_name)
 
sheet.insert_bitmap(icon_file_name, currentRow, currentColumn)
 
#
# Тут конец цикла для перебора ячеек
#
 
# Теперь иконку можно удалить
import os
if os.path.exist(icon_file_name):
   os.remove(icon_file_name)
 

Если у sheet есть метод для вставки иконки как байтового массива, то лучше им воспользоваться, чем создавать тот времененный файл иконки
Записан

Dr.robot
Гость
« Ответ #4 : Январь 30, 2017, 20:55 »

т.е. sheet.insert_bitmap("sym1.bmp",1,1) берет файл sym1.bmp, который лежит в папке с скриптом и вставляет в первую ячейку первой строки?
Да именно так.
Но почему когда я делаю вот так
Код
Python
def save_file(self):
       filename = (QFileDialog.getSaveFileName(self, 'Сохранить', '', ".xls(*.xls)"))
       wbk = xlwt.Workbook()
       sheet = wbk.add_sheet("схема", cell_overwrite_ok=True)
 
       for currentColumn in range(self.table.columnCount()):
           for currentRow in range(self.table.rowCount()):
 
               my_icon = self.table.item(currentRow, currentColumn)
               sheet.insert_bitmap(my_icon, currentRow, currentColumn)
               wbk.save(filename)
Он мне выдает ошибку
Traceback (most recent call last):
  File "C:/Users/Desktop/game_ower/troubletable.py", line 83, in save_file
    sheet.insert_bitmap(my_icon, currentRow, currentColumn)
  File "C:\Python34\lib\site-packages\xlwt\Worksheet.py", line 1122, in insert_bitmap
    bmp = Bitmap.ImDataBmpRecord(filename)
  File "C:\Python34\lib\site-packages\xlwt\Bitmap.py", line 273, in __init__
    self.width, self.height, self.size, data = _process_bitmap(filename)
  File "C:\Python34\lib\site-packages\xlwt\Bitmap.py", line 195, in _process_bitmap
    with open(bitmap, "rb") as fh:
TypeError: invalid file: <PyQt4.QtGui.QTableWidgetItem object at 0x0000000003AB64C8>
Файла нет =( Получается я не сохраняю в ячейки QtableWWidget картинки а просто их там рисую. беда...

А можно по подробнее что вы предложили а то я не совсем понял.
« Последнее редактирование: Январь 30, 2017, 21:09 от Dr.robot » Записан
gil9red
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 1805



Просмотр профиля WWW
« Ответ #5 : Январь 31, 2017, 09:00 »

Вы наверное меня не читаете

Вот это я предложил сделать:
Код
Python
item = self.table.item(currentRow, currentColumn)
 
# Сохранение иконки ячейки в файл
img = item.data(Qt.DecorationRole)
img.save(icon_file_name)
 
sheet.insert_bitmap(icon_file_name, currentRow, currentColumn)
 

Вот сделали вы:
Код
Python
my_icon = self.table.item(currentRow, currentColumn)
sheet.insert_bitmap(my_icon, currentRow, currentColumn)

Ваш код, конечно, не будет работать ведь либа xlwt не умеет (и не должна) работать с объектами либы PyQt4
Записан

Dr.robot
Гость
« Ответ #6 : Февраль 05, 2017, 18:36 »

То что вы предложили не работает и не подходит для моей задачи.
Дело в том что я сохраняю  вот это <PyQt4.QtGui.QTableWidgetItem object at 0x0000000003AB64C8> вместо картинки.
Я даже тестировал и сохранял в обычный текстовой файл и получал тоже самое.
Если xlwt не подходит то есть что ни будь другое? Мне даже не обязательно в табличный формат. Главное записать и считать.
Помогите я уже все перепробовал. Просто ступор какой то ни кто не знает...
Записан
gil9red
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 1805



Просмотр профиля WWW
« Ответ #7 : Февраль 06, 2017, 08:26 »

Вы ошибаетесь и если приложите свой код, который после моих советов, все-равно не хочет работать, то поразбираемся
А сохранять таблицу можно в XML или JSON
текст ячеек просто сохранить, а их иконки сохранять как base64


И на будущее, если проблема в вопросе затягивается, то советую прикладывать минимальных проект с проблемой, тогда желающие помочь, смогут у себя его запускать и так найти причину проблемы будет намного проще, чем давать советы, основанные только на жалобе ТС
« Последнее редактирование: Февраль 06, 2017, 09:36 от gil9red » Записан

Страниц: [1]   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.384 секунд. Запросов: 23.