いいかげん日記

思いついたことをただひたすら書き殴るいいかげんな日記です。

【Python × PyQt5】 google spreadsheet viewerを作る。(その4:ボタンに機能を与える)

前回までのお話】

『っぽい』アプリケーションを作りはじめて10分ほど。 ウィンドウ上にボタンを作ることに成功した。

しかし、このままではボタンを押しても何も起こらない。

そこで、このボタンに機能を与えようと画策するのであった。。。

【今回の課題】

ボタンを作ったからには押したら何か起きてほしい。

ということで、ボタンを押したらテーブルの行なり列なりが増えるようにしてみようか。(ここで2つ目のボタンを設置。詳細は省略)

【コード】

ということで、前回のコードに少し書き加えました。

import sys
from PyQt5.QtCore import *
from PyQt5.QtGui import *
from PyQt5.QtWidgets import *

class SpreadSheetWidget(QWidget):
    def __init__(self, row, col, parent=None):
        QWidget.__init__(self, parent=parent)
        self.setup_ui(row, col)

    def setup_ui(self, row, col):
        self.spreadsheet = QTableWidget(row, col)

        layout = QVBoxLayout()
        layout.addWidget(self.spreadsheet)

        self.setLayout(layout)

    def add_row(self):
        self.row_position = self.spreadsheet.rowCount()
        self.spreadsheet.insertRow(self.row_position)

    def add_col(self):
        self.col_position = self.spreadsheet.columnCount()
        self.spreadsheet.insertColumn(self.col_position)

class AddButtonWidget(QWidget):
    def __init__(self, parent=None):
        QWidget.__init__(self, parent=parent)
        self.setup_ui()

    def setup_ui(self):
        self.add_button_row = QPushButton('Add row', parent=self)
        self.add_button_col = QPushButton('Add col', parent=self)

        layout = QHBoxLayout()
        layout.addWidget(self.add_button_row)
        layout.addWidget(self.add_button_col)

        self.setLayout(layout)

def main():
    app = QApplication(sys.argv)

    main_window = QMainWindow()
    panel = QWidget()
    layout = QVBoxLayout()
    spreadsheet_widget = SpreadSheetWidget(3,4,parent=panel)
    add_button_widget = AddButtonWidget(parent=panel)

    layout.addWidget(spreadsheet_widget)
    layout.addWidget(add_button_widget)

    panel.setLayout(layout)
    main_window.setCentralWidget(panel)

    add_button_widget.add_button_row.clicked.connect(spreadsheet_widget.add_row)
    add_button_widget.add_button_col.clicked.connect(spreadsheet_widget.add_col)

    main_window.show()
    app.exec_()

if __name__ == '__main__':
    main()


----私なりの説明----

前回と何が変わったかというと、(ボタンの追加を除くと)まず、'main()' 関数に次の2行が加わっています。

    add_button_widget.add_button_row.clicked.connect(spreadsheet_widget.add_row)
    add_button_widget.add_button_col.clicked.connect(spreadsheet_widget.add_col)

これは、

'add_button_widget' というオブジェクトの中の 'add_button_row' というボタンがクリックされることは、'spreadsheet_widget' オブジェクトの中の 'add_row' メソッドを呼び出すことを意味することにしましょう(1行目)。

'add_button_widget' というオブジェクトの中の 'add_button_col' というボタンがクリックされることは、'spreadsheet_widget' オブジェクトの中の 'add_col' メソッドを呼び出すことを意味することにしましょう(2行目)。

という意味。

さて、'spreadsheet_widget' の中の 'add_row' と 'add_col' というものが何処にあったっけ?ということで、探しに行きます。

'main()' 関数の中の記述

    spreadsheet_widget = SpreadSheetWidget(3,4,parent=panel)

から、 'spreadsheet_widget' というのは、'SpreadSheetWidget' クラスのインスタンスだということがわかって、「じゃあ 'SpreadSheetWidget' クラスの中に定義されているメソッドだな」ということで、 'SpreadSheetWidget' クラスを見に行くと、こんな記述がある。

    def add_row(self):
        self.row_position = self.spreadsheet.rowCount()
        self.spreadsheet.insertRow(self.row_position)

    def add_col(self):
        self.col_position = self.spreadsheet.columnCount()
        self.spreadsheet.insertColumn(self.col_position)

確かに、 'SpreadSheetWidget' クラスに 'add_row' メソッドと 'add_col' メソッドが加わっている。

この1行目では、'add_row' メソッドを定義することを宣言しており、2行目で、テーブル 'self.spreadsheet' の行数を 'self.row_position' という名前で呼ぶことにしている。

そして、テーブル 'self.spreadsheet' の最終行('self.row_position' 行目)に新しい行を追加しているらしい(insertRow())。

同様に、5行目以降で 'add_col' の定義が書かれている。


まとめると、'add_button_row' をクリックすることは、この 'add_row' メソッドを呼び出すことになり、それはつまり、テーブルの最終行に新規の行を加えることになる。

同様に、'add_button_col' をクリックすることは、 'add_col' メソッドを呼び出すことになり、それはつまり、テーブルの最終列に新規の列を加えることになる。


こうして、ボタンに機能が加わったのであった。

【外観】

このコードを実行するとこんなウィンドウが出ます。 f:id:theta_proto:20180827212455j:plain

'Add row' という文字が書かれたボタン(= 'add_button_widget' の中の 'add_button_row')を押したあとがこれ f:id:theta_proto:20180827212728j:plain

おー、行が増えた!   (to be continued...)