Skip to content

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also .

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also .
...
  • 8 commits
  • 9 files changed
  • 0 commit comments
  • 1 contributor
View
12 frescobaldi_app/autocomplete/analyzer.py
@@ -192,6 +192,16 @@ def music_glyph(self):
self.column = self.tokens[i + 4].pos
return completiondata.music_glyphs
+def midi_instrument(self):
+ """Complete midiInstrument = #"... """
+ try:
+ i = self.tokens.index('midiInstrument', -7, -2)
+ except ValueError:
+ return
+ if self.last != '"':
+ self.column = self.lastpos
+ return completiondata.midi_instruments
+
def scheme_word(self):
"""Complete scheme word from scheme functions, etc."""
if isinstance(self.last, scm.Word):
@@ -429,6 +439,7 @@ def scheme_other(self):
engraver,
clef,
repeat,
+ midi_instrument,
),
lp.ParseClef: (
clef,
@@ -444,6 +455,7 @@ def scheme_other(self):
),
scm.ParseString: (
music_glyph,
+ midi_instrument,
),
lp.ParseLyricMode: (
lyricmode,
View
2 frescobaldi_app/autocomplete/completiondata.py
@@ -210,3 +210,5 @@ def lilypond_grob_properties(grob):
music_glyphs = listmodel.ListModel(ly.data.music_glyphs())
+midi_instruments = listmodel.ListModel(ly.words.midi_instruments)
+
View
14 frescobaldi_app/helpbrowser/__init__.py
@@ -40,6 +40,7 @@ def __init__(self, mainwindow):
mainwindow.addDockWidget(Qt.RightDockWidgetArea, self)
ac = self.actionCollection = Actions()
actioncollectionmanager.manager(mainwindow).addActionCollection(ac)
+ ac.help_lilypond_doc.triggered.connect(self.activate)
def translateUI(self):
self.setWindowTitle(_("Help Browser"))
@@ -60,19 +61,24 @@ def createActions(self, parent=None):
self.help_back = QAction(parent)
self.help_forward = QAction(parent)
self.help_home = QAction(parent)
- self.help_home_lilypond = QAction(parent)
+ self.help_lilypond_doc= QAction(parent)
+ self.help_lilypond_context = QAction(parent)
self.help_back.setIcon(icons.get("go-previous"))
self.help_forward.setIcon(icons.get("go-next"))
self.help_home.setIcon(icons.get("go-home"))
- self.help_home_lilypond.setIcon(icons.get("lilypond-run"))
+ self.help_lilypond_doc.setIcon(icons.get("lilypond-run"))
+
+ self.help_lilypond_doc.setShortcut(QKeySequence("F9"))
+ self.help_lilypond_context.setShortcut(QKeySequence("Shift+F9"))
def translateUI(self):
self.help_back.setText(_("Back"))
self.help_forward.setText(_("Forward"))
- # L10N: Home page of the Frescobaldi manual
+ # L10N: Home page of the LilyPond manual
self.help_home.setText(_("Home"))
- self.help_home_lilypond.setText(_("LilyPond"))
+ self.help_lilypond_doc.setText(_("&LilyPond Documentation"))
+ self.help_lilypond_context.setText(_("&Contextual LilyPond Help"))
View
8 frescobaldi_app/helpbrowser/browser.py
@@ -30,8 +30,6 @@
import network
-from . import html
-
class Browser(QWidget):
"""We use an embedded QMainWindow so we can add a toolbar nicely."""
@@ -51,7 +49,6 @@ def __init__(self, dockwidget):
ac.help_back.triggered.connect(self.webview.back)
ac.help_forward.triggered.connect(self.webview.forward)
ac.help_home.triggered.connect(self.showHomePage)
- ac.help_home_lilypond.triggered.connect(self.showLilyPondHome)
self.webview.page().setNetworkAccessManager(network.accessmanager())
self.webview.page().setLinkDelegationPolicy(QWebPage.DelegateAllLinks)
@@ -64,7 +61,6 @@ def __init__(self, dockwidget):
tb.addAction(ac.help_forward)
tb.addSeparator()
tb.addAction(ac.help_home)
- tb.addAction(ac.help_home_lilypond)
dockwidget.mainwindow().iconSizeChanged.connect(self.updateToolBarSettings)
dockwidget.mainwindow().toolButtonStyleChanged.connect(self.updateToolBarSettings)
@@ -103,10 +99,6 @@ def sourceViewer(self):
return self._sourceviewer
def showHomePage(self):
- """Shows an initial welcome page."""
- self.webview.load(QUrl("fhelp:titlepage"))
-
- def showLilyPondHome(self):
"""Shows the homepage of the LilyPond documentation."""
#self.webview.load(QUrl("http://lilypond.org/doc")) # TEMP!!!
self.webview.load(QUrl.fromLocalFile("/usr/share/doc/lilypond/html/index.html")) # TEMP
View
60 frescobaldi_app/helpbrowser/html.py
@@ -1,60 +0,0 @@
-# This file is part of the Frescobaldi project, http://www.frescobaldi.org/
-#
-# Copyright (c) 2008 - 2011 by Wilbert Berendsen
-#
-# This program is free software; you can redistribute it and/or
-# modify it under the terms of the GNU General Public License
-# as published by the Free Software Foundation; either version 2
-# of the License, or (at your option) any later version.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with this program; if not, write to the Free Software
-# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
-# See http://www.gnu.org/licenses/ for more information.
-
-"""
-Generates HTML on the fly for help browser, served via a custom fhelp: url scheme
-"""
-
-from __future__ import unicode_literals
-
-import info
-import network
-
-
-def fhelp(url):
- """Returns HTML for custom fhelp: urls."""
- path = url.path()
- if path == "titlepage":
- return titlepage()
-
-
-# install the custom url scheme
-network.accessmanager().registerHtmlHandler("fhelp", fhelp)
-
-
-
-def titlepage():
-
- title = _("Documentation")
- versioninfo = _("{appname} version {version}").format(appname = info.appname, version = info.version)
-
- return titlepage_template.format(**locals())
-
-
-
-titlepage_template = """\
-<html><body>
-<h1>{title}</h1>
-<p>{versioninfo}</p>
-</body></html>
-"""
-
-
-
-
View
164 frescobaldi_app/helpbrowser/lilydoc.py
@@ -0,0 +1,164 @@
+# This file is part of the Frescobaldi project, http://www.frescobaldi.org/
+#
+# Copyright (c) 2008 - 2011 by Wilbert Berendsen
+#
+# This program is free software; you can redistribute it and/or
+# modify it under the terms of the GNU General Public License
+# as published by the Free Software Foundation; either version 2
+# of the License, or (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+# See http://www.gnu.org/licenses/ for more information.
+
+"""
+Manage access to LilyPond documentation.
+"""
+
+from __future__ import unicode_literals
+
+import os
+import re
+
+from PyQt4.QtCore import pyqtSignal, QObject, QSettings, QUrl
+
+import network
+import util
+
+
+def urls():
+ """Returns a list of QUrls where documentation can be found.
+
+ Remote urls (from the users settings) are not checked but simply returned.
+ For user-set local directories, if the directory itself does not contain
+ LilyPond documentation, all directories one level deep are searched.
+
+ This makes it possible to set one directory for local documentation and
+ put there multiple sets of documentation in subdirectories (e.g. with the
+ version number in the path name).
+
+ The paths in the settings are read, and also the usual system directories
+ are scanned.
+
+ """
+ user_paths = QSettings().value("documentation/paths", []) or []
+ system_prefixes = [p for p in (
+ '/usr',
+ '/usr/local',
+ '/usr/share/doc',
+ '/usr/doc',
+ ) if os.path.isdir(p)]
+ # split in local and non-local ones (local are preferred)
+ user_prefixes = []
+ local = []
+ remote = []
+ for p in user_paths:
+ user_prefixes.append(p) if os.path.isdir(p) else remote.append(p)
+
+ # now find all instances of LilyPond documentation in the local paths
+ def paths(path):
+ """Yields possible places where LilyPond documentation could live."""
+ yield path
+ path = os.path.join(path, 'share', 'doc', 'lilypond', 'html')
+ yield path
+ yield os.path.join(path, 'offline-root')
+
+ def find(path):
+ """Finds LilyPond documentation."""
+ for p in paths(path):
+ if os.path.isdir(os.path.join(p, 'Documentation')):
+ return p
+
+ # search in the user-set directories, if no docs, scan one level deeper
+ for p in user_prefixes:
+ n = find(p)
+ if n:
+ local.append(n)
+ elif p not in system_prefixes:
+ for name, dirs, files in os.walk(p):
+ for d in sorted(dirs, key=util.naturalsort):
+ n = find(os.path.join(p, d))
+ if n:
+ local.append(n)
+ break
+ # now add the system directories if documentation is found there
+ for p in system_prefixes:
+ if p not in user_prefixes:
+ n = find(p)
+ if n:
+ local.append(n)
+ urls = []
+ urls.extend(map(QUrl.fromLocalFile, local))
+ urls.extend(map(QUrl, remote))
+ return urls
+
+
+
+class Documentation(QObject):
+ """An instance of LilyPond documentation."""
+ versionLoaded = pyqtSignal(bool)
+
+ def __init__(self, url):
+ QObject.__init__(self)
+ self._url = url
+ self._localFile = url.toLocalFile()
+ self._versionString = None
+
+ # determine version
+ url = self.url()
+ sep = '/' if not url.path().endswith('/') else ''
+ url.setPath(url.path() + sep + 'VERSION')
+ reply = self._versionReply = network.get(url)
+ if reply.isFinished():
+ self._versionReplyFinished()
+ else:
+ reply.finished.connect(self._versionReplyFinished)
+
+ def url(self):
+ return QUrl(self._url)
+
+ def home(self):
+ """Returns the url with 'Documentation' appended."""
+ url = self.url()
+ sep = '/' if not url.path().endswith('/') else ''
+ url.setPath(url.path() + sep + 'Documentation')
+ return url
+
+ def _versionReplyFinished(self):
+ if self._versionReply.error():
+ self._versionString = ''
+ else:
+ self._versionString = bytes(self._versionReply.readAll()).strip()
+ self.versionLoaded.emit(bool(self._versionString))
+ self._versionReply.deleteLater()
+
+ def versionString(self):
+ """Returns the version as a string.
+
+ If the version is not yet determined, returns None.
+ If the version could not be determined, returns the empty string.
+
+ """
+ return self._versionString
+
+ def version(self):
+ """Returns the version as a tuple of ints.
+
+ If the version is not yet determined, returns None.
+ If the version could not be determined, returns the empty tuple.
+
+ """
+ if self._versionString is not None:
+ return tuple(map(int, re.findall(br"\d+", self._versionString)))
+
+ def isLocal(self):
+ """Returns True if the documentation is on the local system."""
+ return bool(self._localFile)
+
+
View
3 frescobaldi_app/menu.py
@@ -303,6 +303,9 @@ def menu_help(mainwindow):
m.addAction(ac.help_manual)
m.addAction(ac.help_whatsthis)
m.addSeparator()
+ m.addAction(panels.manager(mainwindow).helpbrowser.actionCollection.help_lilypond_doc)
+ m.addAction(panels.manager(mainwindow).helpbrowser.actionCollection.help_lilypond_context)
+ m.addSeparator()
m.addAction(ac.help_bugreport)
m.addSeparator()
m.addAction(ac.help_about)
View
4 frescobaldi_app/musicpreview.py
@@ -148,7 +148,9 @@ def setDocuments(self, pdfs):
self._view.clear()
def selectDocument(self, index):
- self._view.load(self._documents[index].document())
+ doc = self._documents[index].document()
+ if doc:
+ self._view.load(doc)
def cleanup(self):
if self._running:
View
55 frescobaldi_app/preferences/paths.py
@@ -29,6 +29,7 @@
import app
import icons
import widgets.listedit
+import widgets.dialog
import preferences
@@ -40,6 +41,7 @@ def __init__(self, dialog):
self.setLayout(layout)
layout.addWidget(HyphenPaths(self))
+ layout.addWidget(LilyDocPaths(self))
layout.addStretch(1)
@@ -74,3 +76,56 @@ def saveSettings(self):
s.remove("paths")
+class LilyDocPaths(preferences.Group):
+ def __init__(self, page):
+ super(LilyDocPaths, self).__init__(page)
+
+ layout = QVBoxLayout()
+ self.setLayout(layout)
+
+ self.paths = LilyDocPathsList()
+ self.paths.changed.connect(self.changed)
+ layout.addWidget(self.paths)
+
+ app.translateUI(self)
+
+ def translateUI(self):
+ self.setTitle(_("LilyPond Documentation"))
+
+ def loadSettings(self):
+ s = QSettings()
+ s.beginGroup("documentation")
+ self.paths.setValue(s.value("paths", []) or [])
+
+ def saveSettings(self):
+ s = QSettings()
+ s.beginGroup("documentation")
+ paths = self.paths.value()
+ if paths:
+ s.setValue("paths", paths)
+ else:
+ s.remove("paths")
+
+
+class LilyDocPathsList(widgets.listedit.ListEdit):
+ def openEditor(self, item):
+
+ dlg = widgets.dialog.Dialog(self,
+ _("Please enter a local path or a URL:"),
+ app.caption("LilyPond Documentation"),
+ icon = icons.get('lilypond-run'))
+ urlreq = widgets.urlrequester.UrlRequester()
+ urlreq.lineEdit.setCompleter(QCompleter([
+ "http://lilypond.org/doc/v2.12/",
+ "http://lilypond.org/doc/v2.14/",
+ "http://lilypond.org/doc/v2.15/",
+ ], urlreq.lineEdit))
+ dlg.setMainWidget(urlreq)
+ urlreq.setMinimumWidth(320)
+ urlreq.lineEdit.setFocus()
+ if dlg.exec_():
+ item.setText(urlreq.path())
+ return True
+ return False
+
+

No commit comments for this range

Something went wrong with that request. Please try again.