--- Title: scieditor2 06 Author: yamasyuh68 Web: https://mimemo.io/m/2ZJDal8KVZoPKMR --- 190907 - 通常 https://live.staticflickr.com/65535/48692833191_1904e583e2_b.jpg - 左のタブ切り替え https://live.staticflickr.com/65535/48692833186_3f3850de7b_b.jpg - Scintilla.py ``` import sys ,os ,ctypes , io,subprocess from PyQt5 import QtCore, QtWidgets from PyQt5.QtWidgets import QApplication,QWidget,QMainWindow,QSizePolicy,QVBoxLayout, QTreeWidgetItem,QLabel,\ QMenu,QAction from PyQt5.Qsci import QsciScintilla from PyQt5.QtCore import Qt , QSettings,QSize,QRectF , QTimer,QByteArray from PyQt5.QtGui import QKeyEvent, QStandardItem ,QStandardItemModel,QPixmap,QPainter,QBrush ,QPalette,QColor,\ QCursor from Scintilla_subclass import qsc from Scintilla_sql import settingsdb import ui class MainWindow(QMainWindow): TAB_NUM=0 def __init__(self, parent=None): super(MainWindow, self).__init__(parent) self.ui = ui.Ui_MainWindow() # <--------------------------- self.ui.setupUi(self) self.currentSci = None self.ui.treeWidget.header().setSectionHidden(1,1) self.ui.listView.LDclicked.connect(self.fileload) self.label=QLabel() self.ui.statusbar.addPermanentWidget(self.label,2) self.label2=QLabel() self.ui.statusbar.addPermanentWidget(self.label2,1) self.label3=QLabel() self.ui.statusbar.addPermanentWidget(self.label3,1) self.db=settingsdb() self.loadini() self.fav=[] self.loadfav() self.ui.listWidget.setContextMenuPolicy(Qt.CustomContextMenu) self.ui.listWidget.customContextMenuRequested.connect(self.favmenu ) def loadfav(self): fname=sys.argv[0][:len(sys.argv[0])-3]+'.ini' # 拡張子が.py の三文字の場合 f=open(fname,'r') # 読み込み専用 self.ui.listWidget.clear() for line in f: if(line.startswith('')==True): line=line.replace('','') line = line.replace('\n','') # これで改行取れるかな?? line = line.replace('\r','') a = os.path.split(line) self.ui.listWidget.addItem(a[1]) self.fav.append(line) # data入れれないみたいなのでここに保存 def favmenu(self,e): menu=QMenu() action = QAction('Reload', self) action.triggered.connect(self.loadfav) menu.addAction(action) action = QAction('OpenFolder', self) action.triggered.connect(self.openfolder) menu.addAction(action) menu.exec_(QCursor.pos ()) def openfolder(self): f=os.path.split(self.fav[self.ui.listWidget.currentRow()] ) subprocess.Popen( ('explorer' , f[0] ) ) def loadini(self): try: settings=self.db.gload() self.restoreGeometry( settings[0]) self.ui.splitter.restoreState(settings[1]) self.ui.splitter_2.restoreState(settings[2]) except: print('main loadini fail') pass def ListDClicked(self,item): self.fileload(self.fav[item.row()]) def analyztree(self): self.ui.treeWidget.clear() line = ctypes.create_string_buffer(128) # これくらいで確保しておく string='.' for i in range(0,self.currentSci.PropDict['Lines']): num=self.currentSci.SendScintilla(2350,i) # SCI_LINELENGTH if(num>127): # print(i) continue num=self.currentSci.SendScintilla(2153,i,line) # SCI_GETLINE line[num]=0 linet=line.value.decode(errors='replace') linet = linet.replace('\n','') # これで改行取れるかな?? linet = linet.replace('\r','') countstring=string # line=self.currentSci.GetLineText(i) if(linet.startswith(countstring)==False): # 1 行頭が '.' でなければ次の行 continue else: countstring+=string if(linet.startswith(countstring)==False): # 2 treeID1 =QTreeWidgetItem([linet,str(i)]) self.ui.treeWidget.addTopLevelItem(treeID1) continue else: countstring+=string if(linet.startswith(countstring)==False): #3 treeID2 = QTreeWidgetItem([linet ,str(i)]) # root の子供として挿入 treeID1.addChild(treeID2) else: treeID3 = QTreeWidgetItem([linet ,str(i)]) # root の子供として挿入 treeID2.addChild(treeID3) countstring=string def treeClicked(self,item): # tree outline print(item.siblingAtColumn(1).data()) i=int(item.siblingAtColumn(1).data()) firstvisible = i-10 if i-10>0 else 0 # ターゲット行は常に上から10行目に表示する self.currentSci.SendScintilla(2613,firstvisible) # SCI_SETFIRSTVISIBLELINE self.currentSci.SendScintilla(2024,i) # SCI_GOTOLINE 2024 self.currentSci.setFocus() def makenewtab(self,name): # 新規作成時もこれが呼ばれる if not name: name='*New*' self.currentSci = qsc(self) self.ui.tabWidget.addTab(self.currentSci, name) self.ui.tabWidget.setCurrentWidget(self.currentSci) self.__lyt = QVBoxLayout() self.__lyt.setContentsMargins(0, 0, 0, 0) self.__lyt.setSpacing(0) self.currentSci.setLayout(self.__lyt) self.currentSci.dropfile.connect(self.fileload) self.currentSci.message.connect(self.mesfromsci) def tabCloseMessage(self,e): if self.currentSci : self.db.save(( self.currentSci.PropDict['fname'] , self.currentSci.SendScintilla(2008 ) ,# SCI_GETCURRENTPOS self.currentSci.SendScintilla(2152 )) ) # SCI_GETFIRSTVISIBLELINE del self.currentSci self.ui.tabWidget.removeTab(e) # e にタブのインデクス def tabChanged(self,e): # print('tabChanged') try: # タブが無くなったとくはエラー object=self.ui.tabWidget.currentWidget() except: self.ui.treeWidget.clear() return if not object : # タブ作ったときに呼ばれたときは何もしない return self.currentSci=object self.analyztree() self.ShowInfo() def search(self): if self.ui.lineEdit.text(): if self.sender()==self.ui.pushButton : self.searchflag=0 self.currentSci.findFirst ( self.ui.lineEdit.text() , 1,0,0,1 ) else: if self.searchflag==0 : self.currentSci.findFirst ( self.ui.lineEdit.text() , 1,0,0,1,forward=False ) self.searchflag=1 else: self.currentSci.findNext() def replace(self): self.currentSci.replace ( self.ui.lineEdit_3.text()) def ShowInfo(self): self.setWindowTitle(self.currentSci.PropDict['fname']) self.label.setText('{} EOL:{} Lines : {} Length : {}'.format( self.currentSci.PropDict['enc'] , self.currentSci.PropDict['EOL'] , self.currentSci.PropDict['Lines'] , self.currentSci.PropDict['Length'] )) def comp(self,string,id): if id: pal=self.label3.palette() pal.setColor( QPalette.AlternateBase , QColor(Qt.black) ) pal.setColor( QPalette.Foreground , QColor(Qt.red) ) self.label3.setPalette( pal ) self.label3.setText( string ) ti=QTimer() ti.singleShot ( 2000, (lambda : self.comp('',0))) else: self.label3.setText( string ) def mesfromsci(self,string): # message from sci self.comp(string ,0) if string=='save OK': # 保存時 再度アウトライン解析 if ( self.ui.tabWidget.tabText(self.ui.tabWidget.currentIndex() ) ) == '*New*': self.setWindowTitle(self.currentSci.PropDict['fname']) self.ui.tabWidget.setTabText( self.ui.tabWidget.currentIndex() , os.path.split(self.currentSci.PropDict['fname'])[1] ) self.analyztree() def fileload(self,string): # 複数から呼ばれる for i in range( self.ui.tabWidget.count() ): # 重複チェック if string==self.ui.tabWidget.widget(i).PropDict['fname'] : self.ui.tabWidget.setCurrentIndex(i) return a=os.path.split(string) self.makenewtab(a[1]) self.currentSci.load(string) self.ShowInfo() pos=self.db.load(string) try: self.currentSci.SendScintilla(2613,pos[1]) # SCI_SETFIRSTVISIBLELINE self.currentSci.SendScintilla(2025,pos[0]) # SCI_GOTOPOS except Exception as e: # 全ての例外 self.comp(self.print_s(e) ,0) # print(e) self.analyztree() self.currentSci.setFocus() def print_s(self,object): with io.StringIO() as f: sys.stdout = f print(object) text = f.getvalue() sys.stdout = sys.__stdout__ text = text.replace('\n','') # これで改行取れるかな?? text = text.replace('\r','') return text def keyPressEvent_(self, event): print('kitayo') def closeEvent (self,e): self.db.gsave((self.saveGeometry(),self.ui.splitter.saveState(),self.ui.splitter_2.saveState())) if __name__ == '__main__': import sys app = QApplication(sys.argv) main_window = MainWindow() main_window.show() sys.exit(app.exec_()) ``` - Scintilla_subclass.py ``` import sys,ctypes,os,glob,subprocess from PyQt5.Qsci import QsciScintilla,QsciLexerPython,QsciMacro from PyQt5.QtWidgets import QMenu , QListView,QAction,QMessageBox ,QColorDialog from PyQt5.QtCore import Qt,QRectF,QSize , pyqtSignal from PyQt5.QtGui import QCursor ,QFont,QFontMetrics,QColor from PyQt5.Qsci import * from PyQt5.QtGui import QCursor ,QFont,QFontMetrics,QColor , QStandardItem ,QStandardItemModel,QPixmap,\ QPainter,QBrush class qsc(QsciScintilla): ARROW_MARKER_NUM = 8 dropfile = pyqtSignal( str ) message = pyqtSignal( str) def __init__(self, parent): super().__init__( ) # self.setAcceptDrops(True) self.set() self.parent=parent self.PropDict={'fname':'','enc':'','EOL':0,'Lines':0 , 'Length':0 } self.Lsp=False self.wrap=0 self.SendScintilla(self.SCI_SETMODEVENTMASK, self.SC_MOD_INSERTTEXT | self.SC_MOD_DELETETEXT ) self.SCEN_CHANGE.connect(self.modify) def load(self,fname): with open(fname , mode='rb') as f: s=f.read() # bynary encodeType='UTF-8','cp932','UTF-16','EUC-JP' for i,l in enumerate(encodeType) : try : self.setText(s.decode(encoding=l)) self.PropDict['enc'] =l self.PropDict['fname'] =fname self.PropDict['Lines'] =self.lines() self.PropDict['Length'] =self.length() # self.currentSci.PropDict['EOL'] =self.currentSci.GetEOLMode() # self.analyztree() # self.ShowInfo() break except : if i== len(encodeType)-1 : # 全部だめ self.setText('fail to load ... decode error ') else: pass self.markerDeleteAll(0) def modify(self): linenum=self.SendScintilla(self.SCI_LINEFROMPOSITION ,self.SendScintilla(self.SCI_GETCURRENTPOS)) handle = self.markerAdd(linenum, 0) # print('modify'+str(linenum)) def keyPressEvent(self, event): # filter # print(str(event.modifiers())) if (event.key() == Qt.Key_D) and (event.modifiers() & Qt.ControlModifier): self.key_selectword() elif (event.key() == Qt.Key_C) and (event.modifiers() & Qt.ControlModifier): self.key_copy() elif (event.key() == Qt.Key_L) and (event.modifiers() & Qt.ShiftModifier): self.key_toggleEOL() elif (event.key() == Qt.Key_S) and (event.modifiers() & Qt.ControlModifier): self.key_save() elif (event.key() == Qt.Key_1) and (event.modifiers() & Qt.ControlModifier): self.key_color() elif (event.key() == Qt.Key_F1): self.key_toggleEOL() elif (event.key() == Qt.Key_F2): self.linewrpping() else: super(qsc, self).keyPressEvent(event) # send to parent def key_color(self): # color select dialog getcolor = QColorDialog.getColor() colots=getcolor.name() print(colots) def key_copy(self): if( self.SendScintilla(self.SCI_GETCURRENTPOS) == self.SendScintilla(self.SCI_GETANCHOR )): self.SendScintilla(self.SCI_LINECOPY) else : # self.SendScintilla(self.SCI_COPY) super().SendScintilla(self.SCI_COPY) def key_toggleEOL(self): # 改行表示 F1 self.setEolVisibility(not self.eolVisibility()) def linewrpping(self): # 折りたたみ F2 self.wrap=0 if self.wrap==2 else 2 self.setWrapMode(self.wrap) def key_selectword(self): # C-R pos=self.SendScintilla(self.SCI_GETCURRENTPOS) epos=self.SendScintilla(self.SCI_WORDENDPOSITION,pos) spos=self.SendScintilla(self.SCI_WORDSTARTPOSITION, pos) self.SendScintilla(self.SCI_SETSEL,spos,epos) self.SendScintilla(self.SCI_COPY) # copy def key_save(self): if not self.PropDict['fname'] : self.PropDict['fname'] = self.makesavename() self.PropDict['enc'] = 'UTF-8' self.parent.ShowInfo() fname=self.PropDict['fname'] # enc=self.PropDict['enc'] size=self.SendScintilla(self.SCI_GETLENGTH) s = ctypes.create_string_buffer(size+1) # +1 で確保 self.SendScintilla(self.SCI_GETTEXT , size+1 , s) mes='save OK' if self.PropDict['enc'] == 'UTF-8' : with open(fname,'wb') as f :# 書き込み専用 f.write(s) else: try: s=s.value.decode() senc=s.encode(encoding = self.PropDict['enc']) with open(fname,'wb') as f :# 書き込み専用 f.write(senc) except Exception as e: mes=e.reason + ' ' + str(e.start) self.SendScintilla(2025 , e.start ) #SCI_GOTOPOS self.message.emit(mes) if mes=='save OK': self.markerDeleteAll(0) def makesavename(self): dir=os.path.join(os.path.dirname(__file__) , 'txt') n=0 name='{:02}.txt'.format(n) filepath=os.path.join(dir,name) while os.path.exists(filepath): n+=1 filepath=os.path.join(dir,'{:02}.txt'.format(n) ) # print(filepath) return filepath def dragEnterEvent(self,e): #多分すでに実装されてるからいらないんだと思う e.accept() def dropEvent(self,e): string=e.mimeData().text()[8:] string=string.replace('/','//') self.dropfile.emit(string) def set(self): # -------------------設 定------------------------------ font = QFont() font.setFamily('Ms Gothic') # font.setFamily('MS ゴシック') # font.setFixedPitch(True) font.setFixedPitch(False) font.setPointSize(10) self.setFont(font) self.setMarginsFont(font) # Margin 0 is used for line numbers fontmetrics = QFontMetrics(font) self.setMarginsFont(font) self.markerDefine(QsciScintilla.RightArrow, 0) self.setMarginWidth(0, fontmetrics.width("00000") ) self.setMarginLineNumbers(0, True) self.setMarginsForegroundColor(QColor('blue')) self.setMarginsBackgroundColor(QColor("#cccccc")) # Clickable margin 1 for showing markers # self.setMarginSensitivity(1, True) #self.connect(self, # SIGNAL('marginClicked(int, int, Qt::KeyboardModifiers)'), # self.on_margin_clicked) # self.markerDefine(QsciScintilla.ThreeRightArrows, 1) # self.setMarginWidth(1, fontmetrics.width("000") ) # self.setMarkerBackgroundColor(QColor("#ee1111"), self.ARROW_MARKER_NUM) # Brace matching: enable for a brace immediately before or after # the current position self.setBraceMatching(QsciScintilla.SloppyBraceMatch) # Current line visible with special background color self.setCaretLineVisible(True) self.setCaretLineBackgroundColor(QColor("#fff9cb")) #55ffff # Set Python lexer # Set style for Python comments (style number 1) to a fixed-width lexer = QsciLexerPython() lexer.setDefaultFont(font) self.setLexer(lexer) text = bytearray(str.encode("Arial")) # 32, "Courier New" self.SendScintilla(QsciScintilla.SCI_STYLESETFONT, 1, text) # Don't want to see the horizontal scrollbar at all # Use raw message to Scintilla here (all messages are documented # here: http://www.scintilla.org/ScintillaDoc.html) self.SendScintilla(QsciScintilla.SCI_SETHSCROLLBAR, 0) # self.setUtf8(True) ?? self.setWhitespaceVisibility(True) self.setWhitespaceForegroundColor(QColor('#e5e5e5')) #'red' blue#EEEEEE self.setWhitespaceSize(2) class myListView(QListView): LDclicked = pyqtSignal( str ) def __init__(self,p): super().__init__() self.iconsize=70 self.setIconSize(QSize(self.iconsize,self.iconsize)) self.setSpacing(1) self.foldadir=None self.setContextMenuPolicy(Qt.CustomContextMenu) self.customContextMenuRequested.connect(self.cmenu ) def loadfolda(self): # print('kita') model = QStandardItemModel() self.setModel(model) f=os.path.join(os.path.dirname(__file__) , 'txt', '**') self.foldadir=f[:-2] # print(self.foldadir) for i , p in enumerate(glob.iglob(f )): l= os.path.split(p)[1] with open(p,'r',encoding='UTF-8',errors='ignore') as f2: # 指定文字数を読み込む buf=f2.read(35) model.appendRow(QStandardItem(l)) img=QPixmap(self.iconsize,self.iconsize) paint=QPainter() paint.begin(img) paint.setBrush( Qt.white ) paint.setPen( Qt.white ) paint.drawRect(0,0,self.iconsize-1,self.iconsize-1) paint.setPen( Qt.black ) paint.drawRoundedRect(0,0,self.iconsize-1,self.iconsize-1 ,10,10) paint.drawText( QRectF(0,3,self.iconsize-1,self.iconsize-1) , buf) paint.end() model.setData( model.index(i,0) , img , Qt.DecorationRole ) def openfolder(self): subprocess.Popen( ('explorer' , self.foldadir) ) # print(self.foldadir) def browserDclicked(self,index): f=os.path.join(self.foldadir , index.data(Qt.DisplayRole)) self.LDclicked.emit(f) def cmenu (self,e): menu=QMenu(self) action = QAction('DELL', self) action.triggered.connect(self.fileDel) menu.addAction(action) action = QAction('CUT', self) action.triggered.connect(self.fileCut) menu.addAction(action) menu.exec_(QCursor.pos ()) def fileDel(self,index): f=os.path.join(self.foldadir , self.selectedIndexes()[0].data(Qt.DisplayRole)) reply = QMessageBox.question(self, f,"want to DELL ?", QMessageBox.Yes | QMessageBox.No, QMessageBox.No) if reply == QMessageBox.Yes: os.remove(f) self.loadfolda() def fileCut(self,index): pass ``` - Scintilla_sql.py ``` import os , sqlite3 , datetime class settingsdb(): def __init__(self): self.db=os.path.join(os.path.dirname(__file__) , 'settings.db') conn = sqlite3.connect(self.db) c = conn.cursor() c.execute('create table IF NOT EXISTS database(path PRIMARY KEY,line,times,date)') c.execute('create table IF NOT EXISTS general(gpos , splpos1 , splpos2)') c.close() conn.commit() conn.close() def gload(self): conn = sqlite3.connect(self.db) c = conn.cursor() c.execute('select gpos , splpos1 , splpos2 from general ') res=c.fetchall() c.close() conn.close() if res : return res[0] else: return 0 def gsave(self,lists): conn = sqlite3.connect(self.db) c = conn.cursor() c.execute('DELETE FROM general') c.execute( "INSERT INTO general (gpos , splpos1 , splpos2) VALUES (?,?,?)" ,lists) c.close() conn.commit() conn.close() def save(self,lists): conn = sqlite3.connect(self.db) c = conn.cursor() date="{0:%Y%m%d}".format( datetime.datetime.now() ) times=1 try: c.execute( "INSERT INTO database (path,line,page,times,date) VALUES (?,?,?,?,?)" , ( lists[0] , lists[1] , lists[2] , times,date )) except: c.execute('select times from database where path = ?',(lists[0] , )) times=c.fetchone()[0]+1 c.execute('update database set line= ? , page=? , times=? ,date=? where path = ? ', ( lists[1] ,lists[2] , times, date ,lists[0] ) ) c.close() conn.commit() conn.close() # print(line,times) def load(self,fname): conn = sqlite3.connect(self.db) c = conn.cursor() c.execute('select line ,page from database where path = ?',(fname, )) res=c.fetchone() c.close() conn.close() if res : return res else: return 0 ``` - ui.py ``` # -*- coding: utf-8 -*- # Form implementation generated from reading ui file 'ui.ui' # # Created by: PyQt5 UI code generator 5.12 # # WARNING! All changes made in this file will be lost! from PyQt5 import QtCore, QtGui, QtWidgets class Ui_MainWindow(object): def setupUi(self, MainWindow): MainWindow.setObjectName("MainWindow") MainWindow.resize(1086, 653) self.centralwidget = QtWidgets.QWidget(MainWindow) self.centralwidget.setObjectName("centralwidget") self.horizontalLayout = QtWidgets.QHBoxLayout(self.centralwidget) self.horizontalLayout.setContentsMargins(0, 0, 0, 0) self.horizontalLayout.setSpacing(0) self.horizontalLayout.setObjectName("horizontalLayout") self.splitter_2 = QtWidgets.QSplitter(self.centralwidget) self.splitter_2.setOrientation(QtCore.Qt.Horizontal) self.splitter_2.setObjectName("splitter_2") self.splitter = QtWidgets.QSplitter(self.splitter_2) self.splitter.setOrientation(QtCore.Qt.Vertical) self.splitter.setObjectName("splitter") self.tabWidget_3 = QtWidgets.QTabWidget(self.splitter) self.tabWidget_3.setObjectName("tabWidget_3") self.tab_3 = QtWidgets.QWidget() self.tab_3.setObjectName("tab_3") self.verticalLayout = QtWidgets.QVBoxLayout(self.tab_3) self.verticalLayout.setContentsMargins(0, 0, 0, 0) self.verticalLayout.setSpacing(0) self.verticalLayout.setObjectName("verticalLayout") self.treeWidget = QtWidgets.QTreeWidget(self.tab_3) sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Expanding) sizePolicy.setHorizontalStretch(1) sizePolicy.setVerticalStretch(1) sizePolicy.setHeightForWidth(self.treeWidget.sizePolicy().hasHeightForWidth()) self.treeWidget.setSizePolicy(sizePolicy) self.treeWidget.setMaximumSize(QtCore.QSize(16777215, 16777215)) self.treeWidget.setColumnCount(2) self.treeWidget.setObjectName("treeWidget") self.treeWidget.headerItem().setText(0, "1") self.treeWidget.headerItem().setText(1, "2") self.treeWidget.header().setVisible(False) self.verticalLayout.addWidget(self.treeWidget) self.tabWidget_3.addTab(self.tab_3, "") self.tab_4 = QtWidgets.QWidget() self.tab_4.setObjectName("tab_4") self.verticalLayout_2 = QtWidgets.QVBoxLayout(self.tab_4) self.verticalLayout_2.setContentsMargins(0, 0, 0, 0) self.verticalLayout_2.setSpacing(0) self.verticalLayout_2.setObjectName("verticalLayout_2") self.horizontalLayout_2 = QtWidgets.QHBoxLayout() self.horizontalLayout_2.setSpacing(0) self.horizontalLayout_2.setObjectName("horizontalLayout_2") self.pushButton_2 = QtWidgets.QPushButton(self.tab_4) self.pushButton_2.setObjectName("pushButton_2") self.horizontalLayout_2.addWidget(self.pushButton_2) self.lineEdit_2 = QtWidgets.QLineEdit(self.tab_4) self.lineEdit_2.setObjectName("lineEdit_2") self.horizontalLayout_2.addWidget(self.lineEdit_2) self.verticalLayout_2.addLayout(self.horizontalLayout_2) self.horizontalLayout_3 = QtWidgets.QHBoxLayout() self.horizontalLayout_3.setObjectName("horizontalLayout_3") self.pushButton_3 = QtWidgets.QPushButton(self.tab_4) self.pushButton_3.setObjectName("pushButton_3") self.horizontalLayout_3.addWidget(self.pushButton_3) self.pushButton_4 = QtWidgets.QPushButton(self.tab_4) self.pushButton_4.setObjectName("pushButton_4") self.horizontalLayout_3.addWidget(self.pushButton_4) self.verticalLayout_2.addLayout(self.horizontalLayout_3) self.listView = myListView(self.tab_4) sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Preferred, QtWidgets.QSizePolicy.Preferred) sizePolicy.setHorizontalStretch(1) sizePolicy.setVerticalStretch(10) sizePolicy.setHeightForWidth(self.listView.sizePolicy().hasHeightForWidth()) self.listView.setSizePolicy(sizePolicy) self.listView.setMinimumSize(QtCore.QSize(100, 100)) self.listView.setMovement(QtWidgets.QListView.Snap) self.listView.setResizeMode(QtWidgets.QListView.Adjust) self.listView.setLayoutMode(QtWidgets.QListView.SinglePass) self.listView.setViewMode(QtWidgets.QListView.IconMode) self.listView.setObjectName("listView") self.verticalLayout_2.addWidget(self.listView) self.tabWidget_3.addTab(self.tab_4, "") self.tabWidget_2 = QtWidgets.QTabWidget(self.splitter) self.tabWidget_2.setObjectName("tabWidget_2") self.tab = QtWidgets.QWidget() self.tab.setObjectName("tab") self.horizontalLayout_4 = QtWidgets.QHBoxLayout(self.tab) self.horizontalLayout_4.setContentsMargins(0, 0, 0, 0) self.horizontalLayout_4.setSpacing(0) self.horizontalLayout_4.setObjectName("horizontalLayout_4") self.listWidget = QtWidgets.QListWidget(self.tab) sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Expanding) sizePolicy.setHorizontalStretch(1) sizePolicy.setVerticalStretch(1) sizePolicy.setHeightForWidth(self.listWidget.sizePolicy().hasHeightForWidth()) self.listWidget.setSizePolicy(sizePolicy) self.listWidget.setMinimumSize(QtCore.QSize(1, 1)) self.listWidget.setMaximumSize(QtCore.QSize(16777215, 16777215)) self.listWidget.setObjectName("listWidget") self.horizontalLayout_4.addWidget(self.listWidget) self.tabWidget_2.addTab(self.tab, "") self.tab_2 = QtWidgets.QWidget() self.tab_2.setObjectName("tab_2") self.verticalLayout_3 = QtWidgets.QVBoxLayout(self.tab_2) self.verticalLayout_3.setObjectName("verticalLayout_3") self.lineEdit = QtWidgets.QLineEdit(self.tab_2) self.lineEdit.setObjectName("lineEdit") self.verticalLayout_3.addWidget(self.lineEdit) self.horizontalLayout_5 = QtWidgets.QHBoxLayout() self.horizontalLayout_5.setObjectName("horizontalLayout_5") self.pushButton = QtWidgets.QPushButton(self.tab_2) self.pushButton.setObjectName("pushButton") self.horizontalLayout_5.addWidget(self.pushButton) self.pushButton_7 = QtWidgets.QPushButton(self.tab_2) self.pushButton_7.setObjectName("pushButton_7") self.horizontalLayout_5.addWidget(self.pushButton_7) self.verticalLayout_3.addLayout(self.horizontalLayout_5) self.lineEdit_3 = QtWidgets.QLineEdit(self.tab_2) self.lineEdit_3.setObjectName("lineEdit_3") self.verticalLayout_3.addWidget(self.lineEdit_3) self.pushButton_5 = QtWidgets.QPushButton(self.tab_2) self.pushButton_5.setObjectName("pushButton_5") self.verticalLayout_3.addWidget(self.pushButton_5) self.line = QtWidgets.QFrame(self.tab_2) self.line.setFrameShape(QtWidgets.QFrame.HLine) self.line.setFrameShadow(QtWidgets.QFrame.Sunken) self.line.setObjectName("line") self.verticalLayout_3.addWidget(self.line) self.pushButton_6 = QtWidgets.QPushButton(self.tab_2) self.pushButton_6.setObjectName("pushButton_6") self.verticalLayout_3.addWidget(self.pushButton_6) self.tabWidget_2.addTab(self.tab_2, "") self.tabWidget = QtWidgets.QTabWidget(self.splitter_2) self.tabWidget.setMinimumSize(QtCore.QSize(600, 0)) self.tabWidget.setObjectName("tabWidget") self.horizontalLayout.addWidget(self.splitter_2) MainWindow.setCentralWidget(self.centralwidget) self.menubar = QtWidgets.QMenuBar(MainWindow) self.menubar.setGeometry(QtCore.QRect(0, 0, 1086, 17)) self.menubar.setObjectName("menubar") self.menumenu = QtWidgets.QMenu(self.menubar) self.menumenu.setObjectName("menumenu") MainWindow.setMenuBar(self.menubar) self.statusbar = QtWidgets.QStatusBar(MainWindow) self.statusbar.setObjectName("statusbar") MainWindow.setStatusBar(self.statusbar) self.makenewtab = QtWidgets.QAction(MainWindow) self.makenewtab.setObjectName("makenewtab") self.analyzetree = QtWidgets.QAction(MainWindow) self.analyzetree.setObjectName("analyzetree") self.menumenu.addAction(self.makenewtab) self.menumenu.addAction(self.analyzetree) self.menubar.addAction(self.menumenu.menuAction()) self.retranslateUi(MainWindow) self.tabWidget_3.setCurrentIndex(0) self.tabWidget_2.setCurrentIndex(0) self.tabWidget.setCurrentIndex(-1) self.listWidget.doubleClicked['QModelIndex'].connect(MainWindow.ListDClicked) self.tabWidget.tabBarDoubleClicked['int'].connect(MainWindow.tabCloseMessage) self.tabWidget.currentChanged['int'].connect(MainWindow.tabChanged) self.makenewtab.triggered.connect(MainWindow.makenewtab) self.treeWidget.clicked['QModelIndex'].connect(MainWindow.treeClicked) self.pushButton_3.clicked.connect(self.listView.loadfolda) self.listView.doubleClicked['QModelIndex'].connect(self.listView.browserDclicked) self.pushButton.clicked.connect(MainWindow.search) self.pushButton_7.clicked.connect(MainWindow.search) self.pushButton_5.clicked.connect(MainWindow.replace) self.analyzetree.triggered.connect(MainWindow.analyztree) self.pushButton_4.clicked.connect(self.listView.openfolder) QtCore.QMetaObject.connectSlotsByName(MainWindow) def retranslateUi(self, MainWindow): _translate = QtCore.QCoreApplication.translate MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow")) self.tabWidget_3.setTabText(self.tabWidget_3.indexOf(self.tab_3), _translate("MainWindow", "Tab 1")) self.pushButton_2.setText(_translate("MainWindow", "PushButton")) self.pushButton_3.setText(_translate("MainWindow", "load")) self.pushButton_4.setText(_translate("MainWindow", "OpenFolder")) self.tabWidget_3.setTabText(self.tabWidget_3.indexOf(self.tab_4), _translate("MainWindow", "Tab 2")) self.tabWidget_2.setTabText(self.tabWidget_2.indexOf(self.tab), _translate("MainWindow", "Tab 1")) self.pushButton.setText(_translate("MainWindow", "SEARCH")) self.pushButton_7.setText(_translate("MainWindow", "SearchBack")) self.pushButton_5.setText(_translate("MainWindow", "REPLACE")) self.pushButton_6.setText(_translate("MainWindow", "GREP")) self.tabWidget_2.setTabText(self.tabWidget_2.indexOf(self.tab_2), _translate("MainWindow", "Tab 2")) self.menumenu.setTitle(_translate("MainWindow", "menu")) self.makenewtab.setText(_translate("MainWindow", "makenewtab")) self.analyzetree.setText(_translate("MainWindow", "analyzeTree")) from Scintilla_subclass import myListView if __name__ == "__main__": import sys app = QtWidgets.QApplication(sys.argv) MainWindow = QtWidgets.QMainWindow() ui = Ui_MainWindow() ui.setupUi(MainWindow) MainWindow.show() sys.exit(app.exec_()) ``` --- ---> [scieditor2](https://mimemo.io/m/zeXgworpjz4K0Ek)