示例#1
0
        def revisionInfoLayout(repo):
            """
            Return a layout containg the revision information (local and other)
            """
            hbox = QHBoxLayout()
            hbox.setSpacing(0)
            hbox.setContentsMargins(*MARGINS)

            vbox = QVBoxLayout()
            vbox.setContentsMargins(*MARGINS)
            hbox.addLayout(vbox)
            localrevtitle = qtlib.LabeledSeparator(_('Local revision information'))
            localrevinfo = csinfo.create(repo)
            localrevinfo.update(repo[None].p1())
            vbox.addWidget(localrevtitle)
            vbox.addWidget(localrevinfo)
            vbox.addStretch()

            vbox = QVBoxLayout()
            vbox.setContentsMargins(*MARGINS)
            hbox.addLayout(vbox)
            otherrevtitle = qtlib.LabeledSeparator(_('Other revision information'))
            otherrevinfo = csinfo.create(repo)
            otherrevinfo.update(repo[None].p2())

            vbox.addWidget(otherrevtitle)
            vbox.addWidget(otherrevinfo)
            vbox.addStretch()

            return hbox
示例#2
0
    def __init__(self, repoagent, parent):
        super(ResultPage, self).__init__(repoagent, parent)
        self.setTitle(_('Finished'))
        self.setSubTitle(' ')
        self.setFinalPage(True)

        self.setLayout(QVBoxLayout())
        sep = qtlib.LabeledSeparator(_('Backout changeset'))
        self.layout().addWidget(sep)
        bkCsInfo = csinfo.create(self.repo, 'tip', withupdate=True)
        self.layout().addWidget(bkCsInfo)
        self.bkCsInfo = bkCsInfo
        self.layout().addStretch(1)
示例#3
0
    def __init__(self, repoagent, parent):
        super(CommitPage, self).__init__(repoagent, parent)
        self.commitComplete = False

        self.setTitle(_('Commit backout and merge results'))
        self.setSubTitle(' ')
        self.setLayout(QVBoxLayout())
        self.setCommitPage(True)

        repo = repoagent.rawRepo()

        # csinfo
        def label_func(widget, item, ctx):
            if item == 'rev':
                return _('Revision:')
            elif item == 'parents':
                return _('Parents')
            raise csinfo.UnknownItem()

        def data_func(widget, item, ctx):
            if item == 'rev':
                return _('Working Directory'), str(ctx)
            elif item == 'parents':
                parents = []
                cbranch = ctx.branch()
                for pctx in ctx.parents():
                    branch = None
                    if hasattr(pctx, 'branch') and pctx.branch() != cbranch:
                        branch = pctx.branch()
                    parents.append((str(pctx.rev()), str(pctx), branch, pctx))
                return parents
            raise csinfo.UnknownItem()

        def markup_func(widget, item, value):
            if item == 'rev':
                text, rev = value
                if self.wizard() and self.wizard().parentbackout:
                    return '%s (%s)' % (text, rev)
                else:
                    return '<a href="view">%s</a> (%s)' % (text, rev)
            elif item == 'parents':

                def branch_markup(branch):
                    opts = dict(fg='black', bg='#aaffaa')
                    return qtlib.markup(' %s ' % branch, **opts)

                csets = []
                for rnum, rid, branch, pctx in value:
                    line = '%s (%s)' % (rnum, rid)
                    if branch:
                        line = '%s %s' % (line, branch_markup(branch))
                    msg = widget.info.get_data('summary', widget, pctx,
                                               widget.custom)
                    if msg:
                        line = '%s %s' % (line, msg)
                    csets.append(line)
                return csets
            raise csinfo.UnknownItem()

        custom = csinfo.custom(label=label_func,
                               data=data_func,
                               markup=markup_func)
        contents = ('rev', 'user', 'dateage', 'branch', 'parents')
        style = csinfo.panelstyle(contents=contents, margin=6)

        # merged files
        rev_sep = qtlib.LabeledSeparator(_('Working Directory (merged)'))
        self.layout().addWidget(rev_sep)
        bkCsInfo = csinfo.create(repo,
                                 None,
                                 style,
                                 custom=custom,
                                 withupdate=True)
        bkCsInfo.linkActivated.connect(self.onLinkActivated)
        self.layout().addWidget(bkCsInfo)

        # commit message area
        msg_sep = qtlib.LabeledSeparator(_('Commit message'))
        self.layout().addWidget(msg_sep)
        msgEntry = messageentry.MessageEntry(self)
        msgEntry.installEventFilter(qscilib.KeyPressInterceptor(self))
        msgEntry.refresh(repo)
        msgEntry.loadSettings(QSettings(), 'backout/message')

        msgEntry.textChanged.connect(self.completeChanged)
        self.layout().addWidget(msgEntry)
        self.msgEntry = msgEntry

        self.cmd = cmdui.Widget(True, False, self)
        self.cmd.commandFinished.connect(self.onCommandFinished)
        self.cmd.setShowOutput(False)
        self.layout().addWidget(self.cmd)

        def tryperform():
            if self.isComplete():
                self.wizard().next()

        actionEnter = QAction('alt-enter', self)
        actionEnter.setShortcuts(
            [Qt.CTRL + Qt.Key_Return, Qt.CTRL + Qt.Key_Enter])
        actionEnter.triggered.connect(tryperform)
        self.addAction(actionEnter)

        self.skiplast = QCheckBox(
            _('Skip final confirmation page, '
              'close after commit.'))
        checked = QSettings().value('backout/skiplast', False).toBool()
        self.skiplast.setChecked(checked)
        self.layout().addWidget(self.skiplast)

        def eng_toggled(checked):
            if self.isComplete():
                oldmsg = self.msgEntry.text()
                if self.wizard().backoutmergeparentrev:
                    msgset = i18n.keepgettext()._(
                        'Backed out merge changeset: ')
                else:
                    msgset = i18n.keepgettext()._('Backed out changeset: ')
                msg = checked and msgset['id'] or msgset['str']
                if oldmsg and oldmsg != msg:
                    if not qtlib.QuestionMsgBox(
                            _('Confirm Discard Message'),
                            _('Discard current backout message?'),
                            parent=self):
                        self.engChk.blockSignals(True)
                        self.engChk.setChecked(not checked)
                        self.engChk.blockSignals(False)
                        return
                self.msgEntry.setText(msg +
                                      str(self.repo[self.wizard().backoutrev]))
                self.msgEntry.moveCursorToEnd()

        self.engChk = QCheckBox(_('Use English backout message'))
        self.engChk.toggled.connect(eng_toggled)
        engmsg = self.repo.ui.configbool('tortoisehg', 'engmsg', False)
        self.engChk.setChecked(engmsg)
        self.layout().addWidget(self.engChk)
示例#4
0
    def initializePage(self):
        if self.layout():
            return
        self.setTitle(_('Prepare to backout'))
        self.setSubTitle(
            _('Verify backout revision and ensure your working '
              'directory is clean.'))
        self.setLayout(QVBoxLayout())

        self.groups = qtlib.WidgetGroups()

        repo = self.repo
        try:
            bctx = repo[self.wizard().backoutrev]
            pctx = repo['.']
        except error.RepoLookupError:
            qtlib.InfoMsgBox(_('Unable to backout'),
                             _('Backout revision not found'))
            QTimer.singleShot(0, self.wizard().close)
            return

        if pctx == bctx:
            lbl = _('Backing out a parent revision is a single step operation')
            self.layout().addWidget(QLabel(u'<b>%s</b>' % lbl))
            self.wizard().parentbackout = True

        op1, op2 = repo.dirstate.parents()
        if op1 is None:
            qtlib.InfoMsgBox(_('Unable to backout'),
                             _('Backout requires a parent revision'))
            QTimer.singleShot(0, self.wizard().close)
            return

        a = repo.changelog.ancestor(op1, bctx.node())
        if a != bctx.node():
            qtlib.InfoMsgBox(_('Unable to backout'),
                             _('Cannot backout change on a different branch'))
            QTimer.singleShot(0, self.wizard().close)

        ## backout revision
        style = csinfo.panelstyle(contents=csinfo.PANEL_DEFAULT)
        create = csinfo.factory(repo, None, style, withupdate=True)
        sep = qtlib.LabeledSeparator(_('Backout revision'))
        self.layout().addWidget(sep)
        backoutCsInfo = create(bctx.rev())
        self.layout().addWidget(backoutCsInfo)

        ## current revision
        contents = ('ishead', ) + csinfo.PANEL_DEFAULT
        style = csinfo.panelstyle(contents=contents)

        def markup_func(widget, item, value):
            if item == 'ishead' and value is False:
                text = _('Not a head, backout will create a new head!')
                return qtlib.markup(text, fg='red', weight='bold')
            raise csinfo.UnknownItem(item)

        custom = csinfo.custom(markup=markup_func)
        create = csinfo.factory(repo, custom, style, withupdate=True)

        sep = qtlib.LabeledSeparator(_('Current local revision'))
        self.layout().addWidget(sep)
        localCsInfo = create(pctx.rev())
        self.layout().addWidget(localCsInfo)
        self.localCsInfo = localCsInfo

        ## Merge revision backout handling
        if len(bctx.parents()) > 1:
            # Show two radio buttons letting the user which merge revision
            # parent to backout to
            p1rev = bctx.p1().rev()
            p2rev = bctx.p2().rev()

            def setBackoutMergeParentRev(rev):
                self.wizard().backoutmergeparentrev = rev

            setBackoutMergeParentRev(p1rev)

            sep = qtlib.LabeledSeparator(_('Merge parent to backout to'))
            self.layout().addWidget(sep)
            self.layout().addWidget(
                QLabel(
                    _('To backout a <b>merge</b> revision you must select which '
                      'parent to backout to '
                      '(i.e. whose changes will be <i>kept</i>)')))

            self.actionFirstParent = QRadioButton(
                _('First Parent: revision %s (%s)') \
                % (p1rev, str(bctx.p1())), self)
            self.actionFirstParent.setCheckable(True)
            self.actionFirstParent.setChecked(True)
            self.actionFirstParent.setShortcut('CTRL+1')
            self.actionFirstParent.setToolTip(
                _('Backout to the first parent of the merge revision'))
            self.actionFirstParent.clicked.connect(
                lambda: setBackoutMergeParentRev(p1rev))

            self.actionSecondParent = QRadioButton(
                _('Second Parent: revision %s (%s)') % (p2rev, str(bctx.p2())),
                self)
            self.actionSecondParent.setCheckable(True)
            self.actionSecondParent.setShortcut('CTRL+2')
            self.actionSecondParent.setToolTip(
                _('Backout to the second parent of the merge revision'))
            self.actionSecondParent.clicked.connect(
                lambda: setBackoutMergeParentRev(p2rev))

            self.layout().addWidget(self.actionFirstParent)
            self.layout().addWidget(self.actionSecondParent)

        ## working directory status
        sep = qtlib.LabeledSeparator(_('Working directory status'))
        self.layout().addWidget(sep)

        wdbox = QHBoxLayout()
        self.layout().addLayout(wdbox)
        self.wd_status = qtlib.StatusLabel()
        self.wd_status.set_status(_('Checking...'))
        wdbox.addWidget(self.wd_status)
        wd_prog = QProgressBar()
        wd_prog.setMaximum(0)
        wd_prog.setTextVisible(False)
        self.groups.add(wd_prog, 'prog')
        wdbox.addWidget(wd_prog, 1)

        text = _(
            'Before backout, you must <a href="commit"><b>commit</b></a>, '
            '<a href="shelve"><b>shelve</b></a> to patch, '
            'or <a href="discard"><b>discard</b></a> changes.')
        wd_text = QLabel(text)
        wd_text.setWordWrap(True)
        wd_text.linkActivated.connect(self.onLinkActivated)
        self.wd_text = wd_text
        self.groups.add(wd_text, 'dirty')
        self.layout().addWidget(wd_text)

        ## auto-resolve
        autoresolve_chk = QCheckBox(
            _('Automatically resolve merge conflicts '
              'where possible'))
        autoresolve_chk.setChecked(
            repo.ui.configbool('tortoisehg', 'autoresolve', False))
        self.registerField('autoresolve', autoresolve_chk)
        self.layout().addWidget(autoresolve_chk)
        self.autoresolve_chk = autoresolve_chk
        self.groups.set_visible(False, 'dirty')
示例#5
0
    def __init__(self, repoagent, parent, **opts):
        super(RebaseDialog, self).__init__(parent)
        self.setWindowIcon(qtlib.geticon('hg-rebase'))
        f = self.windowFlags()
        self.setWindowFlags(f & ~Qt.WindowContextHelpButtonHint)
        self._repoagent = repoagent
        repo = repoagent.rawRepo()
        self.opts = opts
        self.aborted = False

        box = QVBoxLayout()
        box.setSpacing(8)
        box.setContentsMargins(*(6, ) * 4)
        self.setLayout(box)

        style = csinfo.panelstyle(selectable=True)

        srcb = QGroupBox(_('Rebase changeset and descendants'))
        srcb.setLayout(QVBoxLayout())
        srcb.layout().setContentsMargins(*(2, ) * 4)
        s = opts.get('source', '.')
        source = csinfo.create(self.repo, s, style, withupdate=True)
        srcb.layout().addWidget(source)
        self.layout().addWidget(srcb)

        destb = QGroupBox(_('To rebase destination'))
        destb.setLayout(QVBoxLayout())
        destb.layout().setContentsMargins(*(2, ) * 4)
        d = opts.get('dest', '.')
        dest = csinfo.create(self.repo, d, style, withupdate=True)
        destb.layout().addWidget(dest)
        self.destcsinfo = dest
        self.layout().addWidget(destb)

        sep = qtlib.LabeledSeparator(_('Options'))
        self.layout().addWidget(sep)

        self.keepchk = QCheckBox(_('Keep original changesets'))
        self.keepchk.setChecked(opts.get('keep', False))
        self.layout().addWidget(self.keepchk)

        self.keepbrancheschk = QCheckBox(_('Keep original branch names'))
        self.keepbrancheschk.setChecked(opts.get('keepbranches', False))
        self.layout().addWidget(self.keepbrancheschk)

        self.collapsechk = QCheckBox(_('Collapse the rebased changesets '))
        self.collapsechk.setChecked(opts.get('collapse', False))
        self.layout().addWidget(self.collapsechk)

        self.autoresolvechk = QCheckBox(
            _('Automatically resolve merge conflicts '
              'where possible'))
        self.autoresolvechk.setChecked(
            repo.ui.configbool('tortoisehg', 'autoresolve', False))
        self.layout().addWidget(self.autoresolvechk)

        if 'hgsubversion' in repo.extensions():
            self.svnchk = QCheckBox(
                _('Rebase unpublished onto Subversion head '
                  '(override source, destination)'))
            self.layout().addWidget(self.svnchk)
        else:
            self.svnchk = None

        self.cmd = cmdui.Widget(True, True, self)
        self.cmd.commandFinished.connect(self.commandFinished)
        self.showMessage.connect(self.cmd.stbar.showMessage)
        self.cmd.stbar.linkActivated.connect(self.linkActivated)
        self.layout().addWidget(self.cmd, 2)

        bbox = QDialogButtonBox()
        self.cancelbtn = bbox.addButton(QDialogButtonBox.Cancel)
        self.cancelbtn.clicked.connect(self.reject)
        self.rebasebtn = bbox.addButton(_('Rebase'),
                                        QDialogButtonBox.ActionRole)
        self.rebasebtn.clicked.connect(self.rebase)
        self.abortbtn = bbox.addButton(_('Abort'), QDialogButtonBox.ActionRole)
        self.abortbtn.clicked.connect(self.abort)
        self.layout().addWidget(bbox)
        self.bbox = bbox

        if self.checkResolve() or not (s or d):
            for w in (srcb, destb, sep, self.keepchk, self.collapsechk,
                      self.keepbrancheschk):
                w.setHidden(True)
            self.cmd.setShowOutput(True)
        else:
            self.showMessage.emit(_('Checking...'))
            self.abortbtn.setEnabled(False)
            self.rebasebtn.setEnabled(False)
            QTimer.singleShot(0, self.checkStatus)

        self.setMinimumWidth(480)
        self.setMaximumHeight(800)
        self.resize(0, 340)
        self.setWindowTitle(_('Rebase - %s') % self.repo.displayname)
示例#6
0
    def __init__(self, repo, parent, **opts):
        super(GraftDialog, self).__init__(parent)
        self.setWindowIcon(qtlib.geticon('hg-transplant'))
        f = self.windowFlags()
        self.setWindowFlags(f & ~Qt.WindowContextHelpButtonHint)
        self.repo = repo
        self._graftstatefile = self.repo.join('graftstate')
        self.opts = opts
        self.aborted = False
        self.valid = True

        destrev = opts.get('dest', '.')
        def cleanrevlist(revlist):
            return [self.repo[rev].rev() for rev in revlist]
        self.sourcelist = cleanrevlist(opts.get('source', ['.']))
        currgraftrevs = self.graftstate()
        if currgraftrevs:
            currgraftrevs = cleanrevlist(currgraftrevs)
            if self.sourcelist != currgraftrevs:
                res = qtlib.CustomPrompt(_('Interrupted graft operation found'),
                    _('An interrupted graft operation has been found.\n\n'
                      'You cannot perform a different graft operation unless '
                      'you abort the interrupted graft operation first.'),
                    self,
                    (_('Continue or abort interrupted graft operation?'),
                     _('Cancel')), 1, 2).run()
                if res != 0:
                    # Cancel
                    self.valid = False
                    return
                # Continue creating the dialog, but use the graft source
                # of the existing, interrupted graft as the source, rather than
                # the one that was passed as an option to the dialog constructor
                self.sourcelist = currgraftrevs

        box = QVBoxLayout()
        box.setSpacing(8)
        box.setContentsMargins(*(6,)*4)
        self.setLayout(box)

        if len(self.sourcelist) > 1:
            listlabel = qtlib.LabeledSeparator(
                _('Graft %d changesets on top of changeset %s') \
                % (len(self.sourcelist), destrev))
            self.layout().addWidget(listlabel)
            self.cslist = cslist.ChangesetList(self.repo)
            self.cslist.update(self.sourcelist)
            self.layout().addWidget(self.cslist)

        style = csinfo.panelstyle(selectable=True)
        self.srcb = srcb = QGroupBox()
        srcb.setLayout(QVBoxLayout())
        srcb.layout().setContentsMargins(*(2,)*4)

        self.source = csinfo.create(self.repo, None, style, withupdate=True)
        self._updateSource(0)
        srcb.layout().addWidget(self.source)
        self.layout().addWidget(srcb)

        destb = QGroupBox( _('To graft destination'))
        destb.setLayout(QVBoxLayout())
        destb.layout().setContentsMargins(*(2,)*4)
        dest = csinfo.create(self.repo, destrev, style, withupdate=True)
        destb.layout().addWidget(dest)
        self.destcsinfo = dest
        self.layout().addWidget(destb)

        sep = qtlib.LabeledSeparator(_('Options'))
        self.layout().addWidget(sep)

        self.autoresolvechk = QCheckBox(_('Automatically resolve merge conflicts '
                                           'where possible'))
        self.autoresolvechk.setChecked(
            repo.ui.configbool('tortoisehg', 'autoresolve', False))
        self.layout().addWidget(self.autoresolvechk)

        self.cmd = cmdui.Widget(True, True, self)
        self.cmd.commandFinished.connect(self.commandFinished)
        self.showMessage.connect(self.cmd.stbar.showMessage)
        self.cmd.stbar.linkActivated.connect(self.linkActivated)
        self.layout().addWidget(self.cmd, 2)

        bbox = QDialogButtonBox()
        self.cancelbtn = bbox.addButton(QDialogButtonBox.Cancel)
        self.cancelbtn.clicked.connect(self.reject)
        self.graftbtn = bbox.addButton(_('Graft'),
                                            QDialogButtonBox.ActionRole)
        self.graftbtn.clicked.connect(self.graft)
        self.abortbtn = bbox.addButton(_('Abort'),
                                            QDialogButtonBox.ActionRole)
        self.abortbtn.clicked.connect(self.abort)
        self.layout().addWidget(bbox)
        self.bbox = bbox

        if self.checkResolve():
            self.abortbtn.setEnabled(True)
        else:
            self.showMessage.emit(_('Checking...'))
            self.abortbtn.setEnabled(False)
            self.graftbtn.setEnabled(False)
            QTimer.singleShot(0, self.checkStatus)

        self.setMinimumWidth(480)
        self.setMaximumHeight(800)
        self.resize(0, 340)
        self.setWindowTitle(_('Graft - %s') % self.repo.displayname)
示例#7
0
    def __init__(self, repoagent, parent=None):
        super(ResolveDialog, self).__init__(parent)
        self._repoagent = repoagent
        repo = repoagent.rawRepo()
        self.setWindowFlags(Qt.Window)
        self.setWindowTitle(_('Resolve Conflicts - %s') % repo.displayname)
        self.setWindowIcon(qtlib.geticon('hg-merge'))

        self.setLayout(QVBoxLayout())
        self.layout().setSpacing(5)

        hbox = QHBoxLayout()
        self.layout().addLayout(hbox)

        self.refreshButton = tb = QToolButton(self)
        tb.setIcon(qtlib.geticon('view-refresh'))
        tb.setShortcut(QKeySequence.Refresh)
        tb.clicked.connect(self.refresh)
        self.stlabel = QLabel()
        hbox.addWidget(tb)
        hbox.addWidget(self.stlabel)

        def revisionInfoLayout(repo):
            """
            Return a layout containg the revision information (local and other)
            """
            hbox = QHBoxLayout()
            hbox.setSpacing(0)
            hbox.setContentsMargins(*MARGINS)

            vbox = QVBoxLayout()
            vbox.setContentsMargins(*MARGINS)
            hbox.addLayout(vbox)
            localrevtitle = qtlib.LabeledSeparator(_('Local revision information'))
            localrevinfo = csinfo.create(repo)
            localrevinfo.update(repo[None].p1())
            vbox.addWidget(localrevtitle)
            vbox.addWidget(localrevinfo)
            vbox.addStretch()

            vbox = QVBoxLayout()
            vbox.setContentsMargins(*MARGINS)
            hbox.addLayout(vbox)
            otherrevtitle = qtlib.LabeledSeparator(_('Other revision information'))
            otherrevinfo = csinfo.create(repo)
            otherrevinfo.update(repo[None].p2())

            vbox.addWidget(otherrevtitle)
            vbox.addWidget(otherrevinfo)
            vbox.addStretch()

            return hbox

        if len(self.repo[None].parents()) > 1:
            self.layout().addLayout(revisionInfoLayout(self.repo))

        unres = qtlib.LabeledSeparator(_('Unresolved conflicts'))
        self.layout().addWidget(unres)

        hbox = QHBoxLayout()
        hbox.setSpacing(0)
        hbox.setContentsMargins(*MARGINS)
        self.layout().addLayout(hbox)

        self.utree = PathsTree(self.repo, self)
        hbox.addWidget(self.utree)

        vbox = QVBoxLayout()
        vbox.setContentsMargins(*MARGINS)
        hbox.addLayout(vbox)
        auto = QPushButton(_('Mercurial Re&solve'))
        auto.setToolTip(_('Attempt automatic (trivial) merge'))
        auto.clicked.connect(lambda: self.merge('internal:merge'))
        manual = QPushButton(_('Tool &Resolve'))
        manual.setToolTip(_('Merge using selected merge tool'))
        manual.clicked.connect(self.merge)
        local = QPushButton(_('&Take Local'))
        local.setToolTip(_('Accept the local file version (yours)'))
        local.clicked.connect(lambda: self.merge('internal:local'))
        other = QPushButton(_('Take &Other'))
        other.setToolTip(_('Accept the other file version (theirs)'))
        other.clicked.connect(lambda: self.merge('internal:other'))
        res = QPushButton(_('&Mark as Resolved'))
        res.setToolTip(_('Mark this file as resolved'))
        res.clicked.connect(self.markresolved)
        vbox.addWidget(auto)
        vbox.addWidget(manual)
        vbox.addWidget(local)
        vbox.addWidget(other)
        vbox.addWidget(res)
        vbox.addStretch(1)
        self.ubuttons = (auto, manual, local, other, res)

        self.utree.setContextMenuPolicy(Qt.CustomContextMenu)
        self.utreecmenu = QMenu(self)
        cmauto = self.utreecmenu.addAction(_('Mercurial Re&solve'))
        cmauto.triggered.connect(lambda: self.merge('internal:merge'))
        cmmanual = self.utreecmenu.addAction(_('Tool &Resolve'))
        cmmanual.triggered.connect(self.merge)
        cmlocal = self.utreecmenu.addAction(_('&Take Local'))
        cmlocal.triggered.connect(lambda: self.merge('internal:local'))
        cmother = self.utreecmenu.addAction(_('Take &Other'))
        cmother.triggered.connect(lambda: self.merge('internal:other'))
        cmres = self.utreecmenu.addAction(_('&Mark as Resolved'))
        cmres.triggered.connect(self.markresolved)
        self.utreecmenu.addSeparator()
        cmdiffLocToAnc = self.utreecmenu.addAction(_('Diff &Local to Ancestor'))
        cmdiffLocToAnc.triggered.connect(self.diffLocToAnc)
        cmdiffOthToAnc = self.utreecmenu.addAction(_('&Diff Other to Ancestor'))
        cmdiffOthToAnc.triggered.connect(self.diffOthToAnc)
        self.umenuitems = (cmauto, cmmanual, cmlocal, cmother, cmres,
                           cmdiffLocToAnc, cmdiffOthToAnc)
        self.utree.customContextMenuRequested.connect(self.utreeMenuRequested)

        self.utree.doubleClicked.connect(self.utreeDoubleClicked)

        res = qtlib.LabeledSeparator(_('Resolved conflicts'))
        self.layout().addWidget(res)

        hbox = QHBoxLayout()
        hbox.setContentsMargins(*MARGINS)
        hbox.setSpacing(0)
        self.layout().addLayout(hbox)

        self.rtree = PathsTree(self.repo, self)
        hbox.addWidget(self.rtree)

        vbox = QVBoxLayout()
        vbox.setContentsMargins(*MARGINS)
        hbox.addLayout(vbox)
        edit = QPushButton(_('&Edit File'))
        edit.setToolTip(_('Edit resolved file'))
        edit.clicked.connect(self.edit)
        v3way = QPushButton(_('3-&Way Diff'))
        v3way.setToolTip(_('Visual three-way diff'))
        v3way.clicked.connect(self.v3way)
        vp0 = QPushButton(_('Diff to &Local'))
        vp0.setToolTip(_('Visual diff between resolved file and first parent'))
        vp0.clicked.connect(self.vp0)
        vp1 = QPushButton(_('&Diff to Other'))
        vp1.setToolTip(_('Visual diff between resolved file and second parent'))
        vp1.clicked.connect(self.vp1)
        ures = QPushButton(_('Mark as &Unresolved'))
        ures.setToolTip(_('Mark this file as unresolved'))
        ures.clicked.connect(self.markunresolved)
        vbox.addWidget(edit)
        vbox.addWidget(v3way)
        vbox.addWidget(vp0)
        vbox.addWidget(vp1)
        vbox.addWidget(ures)
        vbox.addStretch(1)
        self.rbuttons = (edit, vp0, ures)
        self.rmbuttons = (vp1, v3way)

        self.rtree.setContextMenuPolicy(Qt.CustomContextMenu)
        self.rtreecmenu = QMenu(self)
        cmedit = self.rtreecmenu.addAction(_('&Edit File'))
        cmedit.triggered.connect(self.edit)
        cmv3way = self.rtreecmenu.addAction(_('3-&Way Diff'))
        cmv3way.triggered.connect(self.v3way)
        cmvp0 = self.rtreecmenu.addAction(_('Diff to &Local'))
        cmvp0.triggered.connect(self.vp0)
        cmvp1 = self.rtreecmenu.addAction(_('&Diff to Other'))
        cmvp1.triggered.connect(self.vp1)
        cmures = self.rtreecmenu.addAction(_('Mark as &Unresolved'))
        cmures.triggered.connect(self.markunresolved)
        self.rmenuitems = (cmedit, cmvp0, cmures)
        self.rmmenuitems = (cmvp1, cmv3way)
        self.rtree.customContextMenuRequested.connect(self.rtreeMenuRequested)

        self.rtree.doubleClicked.connect(self.vp0)

        hbox = QHBoxLayout()
        hbox.setContentsMargins(*MARGINS)
        hbox.setSpacing(4)
        self.layout().addLayout(hbox)

        self.tcombo = ToolsCombo(self.repo, self)
        hbox.addWidget(QLabel(_('Detected merge/diff tools:')))
        hbox.addWidget(self.tcombo)
        hbox.addStretch(1)

        out = qtlib.LabeledSeparator(_('Command output'))
        self.layout().addWidget(out)
        self.cmd = cmdui.Widget(True, False, self)
        self.cmd.commandFinished.connect(self.refresh)
        self.cmd.setShowOutput(True)
        self.layout().addWidget(self.cmd)

        BB = QDialogButtonBox
        bbox = QDialogButtonBox(BB.Close)
        bbox.rejected.connect(self.reject)
        self.layout().addWidget(bbox)
        self.bbox = bbox

        s = QSettings()
        self.restoreGeometry(s.value('resolve/geom').toByteArray())

        self.refresh()
        self.utree.selectAll()
        self.utree.setFocus()
        repoagent.configChanged.connect(self.configChanged)
        repoagent.repositoryChanged.connect(self.repositoryChanged)
示例#8
0
    def __init__(self, repoagent, parent=None):
        QDialog.__init__(self, parent)

        self.setWindowTitle(_('Reorder Unapplied Patches'))
        self.setWindowFlags(Qt.Window)
        self.setWindowIcon(qtlib.geticon('hg-qreorder'))

        self._repoagent = repoagent
        self.cached = None
        repoagent.repositoryChanged.connect(self.refresh)

        layout = QVBoxLayout()
        layout.setMargin(4)
        self.setLayout(layout)

        hb = QHBoxLayout()
        hb.setMargin(2)
        lbl = QLabel(_('Repository:'))
        hb.addWidget(lbl)
        le = QLineEdit()
        hb.addWidget(le)
        le.setReadOnly(True)
        le.setFont(qtlib.getfont('fontlist').font())
        le.setText(self.repo.displayname)
        le.setFocusPolicy(Qt.NoFocus)
        layout.addLayout(hb)
        hl = qtlib.LabeledSeparator('')
        layout.addWidget(hl)

        class PatchListWidget(QListWidget):
            menuRequested = pyqtSignal(QPoint, object)

            def __init__(self, parent):
                QListWidget.__init__(self, parent)
                self.setCurrentRow(0)

            def contextMenuEvent(self, event):
                i = self.item(self.currentRow())
                if i:
                    self.menuRequested.emit(event.globalPos(), i.patchname)

            def focusInEvent(self, e):
                i = self.item(self.currentRow())
                if i:
                    self.parent().parent().showSummary(i)
                QListWidget.focusInEvent(self, e)

        ugb = QGroupBox(_('Unapplied Patches - drag to reorder'))
        ugb.setLayout(QVBoxLayout())
        ugb.layout().setContentsMargins(*(0, ) * 4)
        self.ulw = PatchListWidget(self)
        self.ulw.setDragDropMode(QListView.InternalMove)
        ugb.layout().addWidget(self.ulw)
        self.ulw.currentItemChanged.connect(
            lambda: self.showSummary(self.ulw.item(self.ulw.currentRow())))
        self.ulw.menuRequested.connect(self.patchlistMenuRequest)
        layout.addWidget(ugb)

        agb = QGroupBox(_('Applied Patches'))
        agb.setLayout(QVBoxLayout())
        agb.layout().setContentsMargins(*(0, ) * 4)
        self.alw = PatchListWidget(self)
        agb.layout().addWidget(self.alw)
        self.alw.currentItemChanged.connect(
            lambda: self.showSummary(self.alw.item(self.alw.currentRow())))
        self.alw.menuRequested.connect(self.patchlistMenuRequest)
        layout.addWidget(agb)

        slbl = QLabel(_('Summary:'))
        layout.addWidget(slbl)
        self.summ = QTextEdit()
        self.summ.setFont(qtlib.getfont('fontcomment').font())
        self.summ.setMinimumWidth(500)  # min 80 chars
        self.summ.setMaximumHeight(100)
        self.summ.setReadOnly(True)
        self.summ.setFocusPolicy(Qt.NoFocus)
        layout.addWidget(self.summ)

        self._readsettings()

        self.refresh()

        # dialog buttons
        BB = QDialogButtonBox
        bb = QDialogButtonBox(BB.Ok | BB.Cancel)
        self.apply_button = bb.button(BB.Apply)
        bb.accepted.connect(self.accept)
        bb.rejected.connect(self.reject)
        bb.button(BB.Ok).setDefault(True)
        layout.addWidget(bb)

        self.alw.setCurrentRow(0)
        self.ulw.setCurrentRow(0)
        self.ulw.setFocus()
示例#9
0
    def __init__(self, repoagent, embedded=False, parent=None):
        super(QQueueDialog, self).__init__(parent)

        self.setWindowIcon(qtlib.geticon('thg-mq'))
        self.setWindowTitle(_('Manage MQ patch queues'))
        self.setWindowFlags(self.windowFlags()
                            & ~Qt.WindowContextHelpButtonHint)

        self._repoagent = repoagent
        repoagent.repositoryChanged.connect(self.reload)
        self.needsRefresh = False

        layout = QVBoxLayout()
        layout.setMargin(4)
        self.setLayout(layout)

        hbr = QHBoxLayout()
        hbr.setMargin(2)
        layout.addLayout(hbr)
        rlbl = QLabel(_('Repository:'))
        hbr.addWidget(rlbl)
        rle = QLineEdit()
        hbr.addWidget(rle)
        rle.setFont(qtlib.getfont('fontlist').font())
        rle.setText(self.repo.displayname)
        rle.setReadOnly(True)
        rle.setFocusPolicy(Qt.NoFocus)

        topsep = qtlib.LabeledSeparator('')
        layout.addWidget(topsep)

        hbl = QHBoxLayout()
        hbl.setMargin(2)
        layout.addLayout(hbl)

        qvb = QVBoxLayout()
        hbl.addLayout(qvb)

        qlbl = QLabel(_('Patch queues:'))
        qvb.addWidget(qlbl)
        ql = QListWidget(self)
        qvb.addWidget(ql)
        ql.currentRowChanged.connect(self.updateUI)

        vbb = QVBoxLayout()
        vbb.setMargin(2)
        qvb.addLayout(vbb)

        hqbtntop = QHBoxLayout()
        vbb.addLayout(hqbtntop)
        hqbtnmid = QHBoxLayout()
        vbb.addLayout(hqbtnmid)
        hqbtnbot = QHBoxLayout()
        vbb.addLayout(hqbtnbot)

        btrel = QPushButton(_('Reload'))
        btrel.clicked.connect(self.reload)
        hqbtntop.addWidget(btrel)
        btact = QPushButton(_('Activate'))
        btact.clicked.connect(self.qqueueActivate)
        hqbtntop.addWidget(btact)
        btadd = QPushButton(_('Add'))
        btadd.clicked.connect(self.qqueueAdd)
        hqbtnmid.addWidget(btadd)
        btren = QPushButton(_('Rename'))
        btren.clicked.connect(self.qqueueRename)
        hqbtnmid.addWidget(btren)
        btdel = QPushButton(_('Delete'))
        btdel.clicked.connect(self.qqueueDelete)
        hqbtnbot.addWidget(btdel)
        btpur = QPushButton(_('Purge'))
        btpur.clicked.connect(self.qqueuePurge)
        hqbtnbot.addWidget(btpur)

        pvb = QVBoxLayout()
        hbl.addLayout(pvb)

        plbl = QLabel(_('Patches:'))
        pvb.addWidget(plbl)
        pl = QListWidget(self)
        pvb.addWidget(pl)

        botsep = qtlib.LabeledSeparator('')
        layout.addWidget(botsep)

        cmd = cmdui.Runner(not embedded, self)
        cmd.setTitle(_('QQueue'))
        cmd.output.connect(self.output)
        cmd.makeLogVisible.connect(self.makeLogVisible)
        cmd.commandFinished.connect(self.qqcmdFinished)

        BB = QDialogButtonBox
        bb = QDialogButtonBox(BB.Close)
        bb.button(BB.Close).clicked.connect(self.close)
        layout.addWidget(bb)

        self.setLayout(layout)
        self.ql = ql
        self.pl = pl
        self.btrel = btrel
        self.btact = btact
        self.btadd = btadd
        self.btren = btren
        self.btdel = btdel
        self.btpur = btpur
        self.bb = bb
        self.cmd = cmd

        self.itemfont = None
        self.itemfontbold = None
        self._readsettings()
        self.reload()
        self.ql.setFocus()
示例#10
0
    def __init__(self, repoagent, parent):
        super(CommitPage, self).__init__(repoagent, parent)

        self.setTitle(_('Commit merge results'))
        self.setSubTitle(' ')
        self.setLayout(QVBoxLayout())
        self.setCommitPage(True)

        repo = repoagent.rawRepo()

        # csinfo
        def label_func(widget, item, ctx):
            if item == 'rev':
                return _('Revision:')
            elif item == 'parents':
                return _('Parents')
            raise csinfo.UnknownItem()

        def data_func(widget, item, ctx):
            if item == 'rev':
                return _('Working Directory'), str(ctx)
            elif item == 'parents':
                parents = []
                cbranch = ctx.branch()
                for pctx in ctx.parents():
                    branch = None
                    if hasattr(pctx, 'branch') and pctx.branch() != cbranch:
                        branch = pctx.branch()
                    parents.append((str(pctx.rev()), str(pctx), branch, pctx))
                return parents
            raise csinfo.UnknownItem()

        def markup_func(widget, item, value):
            if item == 'rev':
                text, rev = value
                return '<a href="view">%s</a> (%s)' % (text, rev)
            elif item == 'parents':

                def branch_markup(branch):
                    opts = dict(fg='black', bg='#aaffaa')
                    return qtlib.markup(' %s ' % branch, **opts)

                csets = []
                for rnum, rid, branch, pctx in value:
                    line = '%s (%s)' % (rnum, rid)
                    if branch:
                        line = '%s %s' % (line, branch_markup(branch))
                    msg = widget.info.get_data('summary', widget, pctx,
                                               widget.custom)
                    if msg:
                        line = '%s %s' % (line, msg)
                    csets.append(line)
                return csets
            raise csinfo.UnknownItem()

        custom = csinfo.custom(label=label_func,
                               data=data_func,
                               markup=markup_func)
        contents = ('rev', 'user', 'dateage', 'branch', 'parents')
        style = csinfo.panelstyle(contents=contents, margin=6)

        # merged files
        rev_sep = qtlib.LabeledSeparator(_('Working Directory (merged)'))
        self.layout().addWidget(rev_sep)
        mergeCsInfo = csinfo.create(repo,
                                    None,
                                    style,
                                    custom=custom,
                                    withupdate=True)
        mergeCsInfo.linkActivated.connect(self.onLinkActivated)
        self.layout().addWidget(mergeCsInfo)
        self.mergeCsInfo = mergeCsInfo

        # commit message area
        msg_sep = qtlib.LabeledSeparator(_('Commit message'))
        self.layout().addWidget(msg_sep)
        msgEntry = messageentry.MessageEntry(self)
        msgEntry.installEventFilter(qscilib.KeyPressInterceptor(self))
        msgEntry.refresh(repo)
        msgEntry.loadSettings(QSettings(), 'merge/message')

        msgEntry.textChanged.connect(self.completeChanged)
        self.layout().addWidget(msgEntry)
        self.msgEntry = msgEntry

        self.cmd = cmdui.Widget(True, False, self)
        self.cmd.commandFinished.connect(self.onCommandFinished)
        self.cmd.setShowOutput(False)
        self.layout().addWidget(self.cmd)

        self.delayednext = False

        def tryperform():
            if self.isComplete():
                self.wizard().next()

        actionEnter = QAction('alt-enter', self)
        actionEnter.setShortcuts(
            [Qt.CTRL + Qt.Key_Return, Qt.CTRL + Qt.Key_Enter])
        actionEnter.triggered.connect(tryperform)
        self.addAction(actionEnter)

        self.skiplast = QCheckBox(
            _('Skip final confirmation page, '
              'close after commit.'))
        checked = QSettings().value('merge/skiplast', False).toBool()
        self.skiplast.setChecked(checked)
        self.layout().addWidget(self.skiplast)

        hblayout = QHBoxLayout()
        self.opts = commit.readrepoopts(self.repo)
        self.optionsbtn = QPushButton(_('Commit Options'))
        self.optionsbtn.clicked.connect(self.details)
        hblayout.addWidget(self.optionsbtn)
        self.optionslabelfmt = _('<b>Selected Options:</b> %s')
        self.optionslabel = QLabel('')
        hblayout.addWidget(self.optionslabel)
        hblayout.addStretch()
        self.layout().addLayout(hblayout)

        self.setButtonText(QWizard.CommitButton, _('Commit Now'))
        # The cancel button does not really "cancel" the merge
        self.setButtonText(QWizard.CancelButton, _('Commit Later'))

        # Update the options label
        self.refresh()
示例#11
0
    def initializePage(self):
        if self.layout():
            return
        self.setTitle(_('Prepare to merge'))
        self.setSubTitle(
            _('Verify merge targets and ensure your working '
              'directory is clean.'))
        self.setLayout(QVBoxLayout())

        repo = self.repo
        contents = ('ishead', ) + csinfo.PANEL_DEFAULT
        style = csinfo.panelstyle(contents=contents)

        def markup_func(widget, item, value):
            if item == 'ishead' and value is False:
                text = _('Not a head revision!')
                return qtlib.markup(text, fg='red', weight='bold')
            raise csinfo.UnknownItem(item)

        custom = csinfo.custom(markup=markup_func)
        create = csinfo.factory(repo, custom, style, withupdate=True)

        ## merge target
        other_sep = qtlib.LabeledSeparator(_('Merge from (other revision)'))
        self.layout().addWidget(other_sep)
        try:
            otherCsInfo = create(self.wizard().otherrev)
            self.layout().addWidget(otherCsInfo)
            self.otherCsInfo = otherCsInfo
        except error.RepoLookupError:
            qtlib.InfoMsgBox(_('Unable to merge'),
                             _('Merge revision not specified or not found'))
            QTimer.singleShot(0, self.wizard().close)

        ## current revision
        local_sep = qtlib.LabeledSeparator(_('Merge to (working directory)'))
        self.layout().addWidget(local_sep)
        localCsInfo = create(self.wizard().localrev)
        self.layout().addWidget(localCsInfo)
        self.localCsInfo = localCsInfo

        ## working directory status
        wd_sep = qtlib.LabeledSeparator(_('Working directory status'))
        self.layout().addWidget(wd_sep)

        self.groups = qtlib.WidgetGroups()

        wdbox = QHBoxLayout()
        self.layout().addLayout(wdbox)
        self.wd_status = qtlib.StatusLabel()
        self.wd_status.set_status(_('Checking...'))
        wdbox.addWidget(self.wd_status)
        wd_prog = QProgressBar()
        wd_prog.setMaximum(0)
        wd_prog.setTextVisible(False)
        self.groups.add(wd_prog, 'prog')
        wdbox.addWidget(wd_prog, 1)

        wd_merged = QLabel(
            _('The working directory is already <b>merged</b>. '
              '<a href="skip"><b>Continue</b></a> or '
              '<a href="discard"><b>discard</b></a> existing '
              'merge.'))
        wd_merged.linkActivated.connect(self.onLinkActivated)
        wd_merged.setWordWrap(True)
        self.groups.add(wd_merged, 'merged')
        self.layout().addWidget(wd_merged)

        text = _(
            'Before merging, you must <a href="commit"><b>commit</b></a>, '
            '<a href="shelve"><b>shelve</b></a> to patch, '
            'or <a href="discard"><b>discard</b></a> changes.')
        wd_text = QLabel(text)
        wd_text.setWordWrap(True)
        wd_text.linkActivated.connect(self.onLinkActivated)
        self.wd_text = wd_text
        self.groups.add(wd_text, 'dirty')
        self.layout().addWidget(wd_text)

        wdbox = QHBoxLayout()
        self.layout().addLayout(wdbox)
        wd_alt = QLabel(_('Or use:'))
        self.groups.add(wd_alt, 'dirty')
        wdbox.addWidget(wd_alt)
        force_chk = QCheckBox(
            _('Force a merge with outstanding changes '
              '(-f/--force)'))
        force_chk.toggled.connect(lambda c: self.completeChanged.emit())
        self.registerField('force', force_chk)
        self.groups.add(force_chk, 'dirty')
        wdbox.addWidget(force_chk)

        ### options
        expander = qtlib.ExpanderLabel(_('Options'), False)
        expander.expanded.connect(self.toggleShowOptions)
        self.layout().addWidget(expander)
        self.expander = expander

        ### discard option
        discard_chk = QCheckBox(
            _('Discard all changes from merge target '
              '(other) revision'))
        self.registerField('discard', discard_chk)
        self.layout().addWidget(discard_chk)
        self.discard_chk = discard_chk

        ## auto-resolve
        autoresolve_chk = QCheckBox(
            _('Automatically resolve merge conflicts '
              'where possible'))
        autoresolve_chk.setChecked(
            repo.ui.configbool('tortoisehg', 'autoresolve', False))
        self.registerField('autoresolve', autoresolve_chk)
        self.layout().addWidget(autoresolve_chk)
        self.autoresolve_chk = autoresolve_chk

        self.groups.set_visible(False, 'dirty')
        self.groups.set_visible(False, 'merged')
        self.toggleShowOptions(self.expander.is_expanded())