Пример #1
0
def _highlight_current_cell(cr, background_area, cell_area, flags):
    """Draws a 'highlighting' background for the cell. Look depends on
    the active theme.
    """

    # Use drawing code/CSS for Entry (reason being that it looks best here)
    dummy_widget = Gtk.Entry()
    style_context = dummy_widget.get_style_context()
    style_context.save()
    # Make it less prominent
    state = Gtk.StateFlags.INSENSITIVE | Gtk.StateFlags.BACKDROP
    style_context.set_state(state)
    color = style_context.get_border_color(state)
    add_css(dummy_widget,
            "* { border-color: rgba(%d, %d, %d, 0.3); }" % (
                    color.red * 255, color.green * 255, color.blue * 255))
    ba = background_area
    ca = cell_area
    # Draw over the left and right border so we don't see the rounded corners
    # and borders. Use height for the overshoot as rounded corners + border
    # should never be larger than the height..
    # Ideally we would draw over the whole background but the cell area only
    # redraws the cell_area so we get leftover artifacts if we draw
    # above/below.
    draw_area = (ba.x - ca.height, ca.y,
                 ba.width + ca.height * 2, ca.height)
    cr.save()
    cr.new_path()
    cr.rectangle(ba.x, ca.y, ba.width, ca.height)
    cr.clip()
    Gtk.render_background(style_context, cr, *draw_area)
    Gtk.render_frame(style_context, cr, *draw_area)
    cr.restore()
    style_context.restore()
Пример #2
0
def _highlight_current_cell(cr, background_area, cell_area, flags):
    """Draws a 'highlighting' background for the cell. Look depends on
    the active theme.
    """

    # Use drawing code/CSS for Entry (reason being that it looks best here)
    dummy_widget = Gtk.Entry()
    style_context = dummy_widget.get_style_context()
    style_context.save()
    # Make it less prominent
    state = Gtk.StateFlags.INSENSITIVE | Gtk.StateFlags.BACKDROP
    style_context.set_state(state)
    color = style_context.get_border_color(state)
    add_css(dummy_widget,
            "* { border-color: rgba(%d, %d, %d, 0.3); }" % (
                    color.red * 255, color.green * 255, color.blue * 255))
    ba = background_area
    ca = cell_area
    # Draw over the left and right border so we don't see the rounded corners
    # and borders. Use height for the overshoot as rounded corners + border
    # should never be larger than the height..
    # Ideally we would draw over the whole background but the cell area only
    # redraws the cell_area so we get leftover artifacts if we draw
    # above/below.
    draw_area = (ba.x - ca.height, ca.y,
                 ba.width + ca.height * 2, ca.height)
    cr.save()
    cr.new_path()
    cr.rectangle(ba.x, ca.y, ba.width, ca.height)
    cr.clip()
    Gtk.render_background(style_context, cr, *draw_area)
    Gtk.render_frame(style_context, cr, *draw_area)
    cr.restore()
    style_context.restore()
Пример #3
0
    def enabled(self):
        self.scrolled_window = Gtk.ScrolledWindow()
        self.scrolled_window.set_policy(Gtk.PolicyType.AUTOMATIC,
                                        Gtk.PolicyType.AUTOMATIC)
        self.adjustment = self.scrolled_window.get_vadjustment()

        self.textview = Gtk.TextView()
        self.textbuffer = self.textview.get_buffer()
        self._italics = self.textbuffer.create_tag("italic",
                                                   style="italic",
                                                   foreground="grey")
        self.textview.set_editable(False)
        self.textview.set_cursor_visible(False)
        self.textview.set_wrap_mode(Gtk.WrapMode.WORD)
        self.textview.set_justification(Gtk.Justification.CENTER)
        self.textview.connect('key-press-event', self.key_press_event_cb)
        add_css(self.textview, "* { padding: 6px; }")
        vbox = Gtk.VBox()
        vbox.pack_start(self.textview, True, True, 0)
        self._edit_button = Button("Edit Lyrics", Icons.EDIT)
        hbox = Gtk.HBox()
        hbox.pack_end(self._edit_button, False, False, 3)
        vbox.pack_start(hbox, False, False, 3)
        self.scrolled_window.add(vbox)
        self.textview.show()

        self.scrolled_window.show()
        self._sig = None
        cur = app.player.info
        if cur is not None:
            cur = SongWrapper(cur)
        self.plugin_on_song_started(cur)
Пример #4
0
    def enabled(self):
        self.scrolled_window = Gtk.ScrolledWindow()
        self.scrolled_window.set_policy(Gtk.PolicyType.AUTOMATIC,
                                        Gtk.PolicyType.AUTOMATIC)
        self.adjustment = self.scrolled_window.get_vadjustment()

        self.textview = Gtk.TextView()
        self.textbuffer = self.textview.get_buffer()
        self._italics = self.textbuffer.create_tag("italic", style="italic",
                                                   foreground="grey")
        self.textview.set_editable(False)
        self.textview.set_cursor_visible(False)
        self.textview.set_wrap_mode(Gtk.WrapMode.WORD)
        self.textview.set_justification(Gtk.Justification.CENTER)
        self.textview.connect('key-press-event', self.key_press_event_cb)
        add_css(self.textview, "* { padding: 6px; }")
        vbox = Gtk.VBox()
        vbox.pack_start(self.textview, True, True, 0)
        self._edit_button = Button("Edit Lyrics", Icons.EDIT)
        hbox = Gtk.HBox()
        hbox.pack_end(self._edit_button, False, False, 3)
        vbox.pack_start(hbox, False, False, 3)
        self.scrolled_window.add(vbox)
        self.textview.show()

        self.scrolled_window.show()
        self._sig = None
        cur = app.player.info
        if cur is not None:
            cur = SongWrapper(cur)
        self.plugin_on_song_started(cur)
Пример #5
0
    def __init__(self, player, library):
        super(PlayControls, self).__init__(spacing=3)

        upper = Gtk.Table(n_rows=1, n_columns=3, homogeneous=True)
        upper.set_row_spacings(3)
        upper.set_col_spacings(3)

        prev = Gtk.Button(relief=Gtk.ReliefStyle.NONE)
        prev.add(
            SymbolicIconImage("media-skip-backward",
                              Gtk.IconSize.LARGE_TOOLBAR))
        upper.attach(prev, 0, 1, 0, 1)

        play = PlayPauseButton()
        upper.attach(play, 1, 2, 0, 1)

        next_ = Gtk.Button(relief=Gtk.ReliefStyle.NONE)
        next_.add(
            SymbolicIconImage("media-skip-forward",
                              Gtk.IconSize.LARGE_TOOLBAR))
        upper.attach(next_, 2, 3, 0, 1)

        lower = Gtk.Table(n_rows=1, n_columns=3, homogeneous=True)
        lower.set_row_spacings(3)
        lower.set_col_spacings(3)

        self.volume = Volume(player)
        self.volume.set_relief(Gtk.ReliefStyle.NONE)
        lower.attach(self.volume, 0, 1, 0, 1)

        # XXX: Adwaita defines a different padding for GtkVolumeButton
        # We force it to 0 here, which works because the other (normal) buttons
        # in the grid set the width/height
        qltk.add_css(
            self.volume, """
            .button {
                padding: 0px;
            }
        """)

        seekbutton = SeekButton(player, library)
        seekbutton.set_relief(Gtk.ReliefStyle.NONE)
        lower.attach(seekbutton, 1, 3, 0, 1)

        self.pack_start(upper, False, True, 0)
        self.pack_start(lower, False, True, 0)

        connect_obj(prev, 'clicked', self.__previous, player)
        self._toggle_id = play.connect('toggled', self.__playpause, player)
        play.add_events(Gdk.EventMask.SCROLL_MASK)
        connect_obj(play, 'scroll-event', self.__scroll, player)
        connect_obj(next_, 'clicked', self.__next, player)
        connect_destroy(player, 'song-started', self.__song_started, next_,
                        play)
        connect_destroy(player, 'paused', self.__on_set_paused_unpaused, play,
                        False)
        connect_destroy(player, 'unpaused', self.__on_set_paused_unpaused,
                        play, True)
Пример #6
0
    def __init__(self, **kwargs):
        super(_SmallImageButton, self).__init__(**kwargs)

        self.set_size_request(26, 26)
        add_css(self, """
            * {
                padding: 0px;
            }
        """)
Пример #7
0
    def __init__(self, **kwargs):
        super().__init__(**kwargs)

        self.set_size_request(26, 26)
        add_css(self, """
            * {
                padding: 0px;
            }
        """)
Пример #8
0
    def __init__(self, player, library):
        super(PlayControls, self).__init__(spacing=3)

        upper = Gtk.Table(n_rows=1, n_columns=3, homogeneous=True)
        upper.set_row_spacings(3)
        upper.set_col_spacings(3)

        prev = Gtk.Button(relief=Gtk.ReliefStyle.NONE)
        prev.add(SymbolicIconImage("media-skip-backward",
                                   Gtk.IconSize.LARGE_TOOLBAR))
        upper.attach(prev, 0, 1, 0, 1)

        play = Gtk.ToggleButton(relief=Gtk.ReliefStyle.NONE)
        play.add(SymbolicIconImage("media-playback-start",
                                   Gtk.IconSize.LARGE_TOOLBAR))
        upper.attach(play, 1, 2, 0, 1)

        next_ = Gtk.Button(relief=Gtk.ReliefStyle.NONE)
        next_.add(SymbolicIconImage("media-skip-forward",
                                    Gtk.IconSize.LARGE_TOOLBAR))
        upper.attach(next_, 2, 3, 0, 1)

        lower = Gtk.Table(n_rows=1, n_columns=3, homogeneous=True)
        lower.set_row_spacings(3)
        lower.set_col_spacings(3)

        self.volume = Volume(player)
        self.volume.set_relief(Gtk.ReliefStyle.NONE)
        lower.attach(self.volume, 0, 1, 0, 1)

        # XXX: Adwaita defines a different padding for GtkVolumeButton
        # We force it to 0 here, which works because the other (normal) buttons
        # in the grid set the width/height
        qltk.add_css(self.volume, """
            .button {
                padding: 0px;
            }
        """)

        seekbar = SeekBar(player, library)
        seekbar.set_relief(Gtk.ReliefStyle.NONE)
        lower.attach(seekbar, 1, 3, 0, 1)

        self.pack_start(upper, False, True, 0)
        self.pack_start(lower, False, True, 0)

        connect_obj(prev, 'clicked', self.__previous, player)
        self._toggle_id = play.connect('toggled', self.__playpause, player)
        play.add_events(Gdk.EventMask.SCROLL_MASK)
        connect_obj(play, 'scroll-event', self.__scroll, player)
        connect_obj(next_, 'clicked', self.__next, player)
        connect_destroy(
            player, 'song-started', self.__song_started, next_, play)
        connect_destroy(
            player, 'paused', self.__on_set_paused_unpaused, play, False)
        connect_destroy(
            player, 'unpaused', self.__on_set_paused_unpaused, play, True)
Пример #9
0
    def __init__(self, parent, player, library):
        super(TopBar, self).__init__()

        # play controls
        control_item = Gtk.ToolItem()
        self.insert(control_item, 0)
        t = PlayControls(player, library.librarian)
        self.volume = t.volume

        # only restore the volume in case it is managed locally, otherwise
        # this could affect the system volume
        if not player.has_external_volume:
            player.volume = config.getfloat("memory", "volume")

        connect_destroy(player, "notify::volume", self._on_volume_changed)
        control_item.add(t)

        self.insert(Gtk.SeparatorToolItem(), 1)

        info_item = Gtk.ToolItem()
        self.insert(info_item, 2)
        info_item.set_expand(True)

        box = Gtk.Box(spacing=6)
        info_item.add(box)
        qltk.add_css(self, "GtkToolbar {padding: 3px;}")

        self._pattern_box = Gtk.VBox()

        # song text
        info_pattern_path = os.path.join(quodlibet.get_user_dir(), "songinfo")
        text = SongInfo(library.librarian, player, info_pattern_path)
        self._pattern_box.pack_start(Align(text, border=3), True, True, 0)
        box.pack_start(self._pattern_box, True, True, 0)

        # cover image
        self.image = CoverImage(resize=True)
        connect_destroy(player, 'song-started', self.__new_song)

        # FIXME: makes testing easier
        if app.cover_manager:
            connect_destroy(
                app.cover_manager, 'cover-changed',
                self.__song_art_changed, library)

        box.pack_start(Align(self.image, border=2), False, True, 0)

        # On older Gtk+ (3.4, at least)
        # setting a margin on CoverImage leads to errors and result in the
        # QL window not being visible for some reason.
        assert self.image.props.margin == 0

        for child in self.get_children():
            child.show_all()

        context = self.get_style_context()
        context.add_class("primary-toolbar")
Пример #10
0
 def _style_lyrics_window(self):
     qltk.add_css(self.textview, """
         #syncLyricsWindow {{
             background-color: {0};
             color: {1};
             font-size: {2}px;
             font-weight: bold;
         }}
     """.format(self._get_background_color(), self._get_text_color(),
                self._get_font_size()))
Пример #11
0
 def _style_lyrics_window(self):
     qltk.add_css(self.textview, """
         #syncLyricsWindow {{
             background-color: {0};
             color: {1};
             font-size: {2}px;
             font-weight: bold;
         }}
     """.format(self._get_background_color(), self._get_text_color(),
                self._get_font_size()))
Пример #12
0
 def _style_lyrics_window(self):
     self.scrolled_window.set_size_request(-1, 2 * self._get_font_size())
     qltk.add_css(
         self.textview, """
         * {{
             background-color: {0};
             color: {1};
             font-size: {2}px;
             font-weight: bold;
         }}
     """.format(self._get_background_color(), self._get_text_color(),
                self._get_font_size()))
Пример #13
0
def Frame(name, widget):
    def hx(value):
        return hex(int(value * 255))[2:]
    f = Gtk.Frame()
    qltk.add_css(f, '* {opacity: 0.9}')
    l = Gtk.Label()
    l.set_markup(util.escape(name))
    qltk.add_css(l, " * {opacity: 0.6; padding: 0px 2px;}")
    f.set_label_widget(l)
    a = Align(top=6, left=12, bottom=6, right=6)
    f.add(a)
    a.add(widget)
    return f
Пример #14
0
def Frame(name, widget):
    def hx(value):
        return hex(int(value * 255))[2:]
    f = Gtk.Frame()
    qltk.add_css(f, '* {opacity: 0.9}')
    l = Gtk.Label()
    l.set_markup(util.escape(name))
    qltk.add_css(l, " * {opacity: 0.6; padding: 0px 2px;}")
    f.set_label_widget(l)
    a = Align(top=6, left=12, bottom=6, right=6)
    f.add(a)
    a.add(widget)
    return f
Пример #15
0
 def _style_lyrics_window(self):
     if self.scrolled_window is None:
         return
     self.scrolled_window.set_size_request(-1, 1.6 * self._get_font_size())
     qltk.add_css(self.textview, """
         * {{
             background-color: {0};
             color: {1};
             font-size: {2}px;
             padding: 0.2em;
         }}
     """.format(self._get_background_color(), self._get_text_color(),
                self._get_font_size()))
Пример #16
0
 def _style_lyrics_window(self):
     if self.scrolled_window is None:
         return
     self.scrolled_window.set_size_request(-1, 1.6 * self._get_font_size())
     qltk.add_css(self.textview, """
         * {{
             background-color: {0};
             color: {1};
             font-size: {2}px;
             padding: 0.2em;
         }}
     """.format(self._get_background_color(), self._get_text_color(),
                self._get_font_size()))
Пример #17
0
 def _style_lyrics_window(self):
     if self.scrolled_window is None:
         return
     self.scrolled_window.set_size_request(-1, 1.5 * self._get_font_size())
     qltk.add_css(
         self.textview, f"""
       * {{
             background-color: {self._get_background_color()};
             color: {self._get_text_color()};
             font-size: {self._get_font_size()}px;
             padding: 0.25rem;
             border-radius: 6px;
         }}
     """)
Пример #18
0
    def __init__(self, parent, player, library):
        super(TopBar, self).__init__()

        # play controls
        control_item = Gtk.ToolItem()
        self.insert(control_item, 0)
        t = PlayControls(player, library.librarian)
        self.volume = t.volume

        # only restore the volume in case it is managed locally, otherwise
        # this could affect the system volume
        if not player.has_external_volume:
            player.volume = config.getfloat("memory", "volume")

        self.volume.connect("value-changed", self._on_volume_changed)
        control_item.add(t)

        self.insert(Gtk.SeparatorToolItem(), 1)

        info_item = Gtk.ToolItem()
        self.insert(info_item, 2)
        info_item.set_expand(True)

        box = Gtk.Box(spacing=6)
        info_item.add(box)
        qltk.add_css(self, "GtkToolbar {padding: 3px;}")

        # song text
        info_pattern_path = os.path.join(const.USERDIR, "songinfo")
        text = SongInfo(library.librarian, player, info_pattern_path)
        box.pack_start(Align(text, border=3), True, True, 0)

        # cover image
        self.image = CoverImage(resize=True)
        connect_destroy(player, 'song-started', self.__new_song)

        # FIXME: makes testing easier
        if app.cover_manager:
            connect_destroy(
                app.cover_manager, 'cover-changed',
                self.__song_art_changed, library)

        self.image.props.margin = 2
        box.pack_start(self.image, False, True, 0)

        for child in self.get_children():
            child.show_all()

        context = self.get_style_context()
        context.add_class("primary-toolbar")
Пример #19
0
    def __init__(self, parent, player, library):
        super(TopBar, self).__init__()

        # play controls
        control_item = Gtk.ToolItem()
        self.insert(control_item, 0)
        t = PlayControls(player, library.librarian)
        self.volume = t.volume

        # only restore the volume in case it is managed locally, otherwise
        # this could affect the system volume
        if not player.has_external_volume:
            player.volume = config.getfloat("memory", "volume")

        self.volume.connect("value-changed", self._on_volume_changed)
        control_item.add(t)

        self.insert(Gtk.SeparatorToolItem(), 1)

        info_item = Gtk.ToolItem()
        self.insert(info_item, 2)
        info_item.set_expand(True)

        box = Gtk.Box(spacing=6)
        info_item.add(box)
        qltk.add_css(self, "GtkToolbar {padding: 3px;}")

        # song text
        info_pattern_path = os.path.join(const.USERDIR, "songinfo")
        text = SongInfo(library.librarian, player, info_pattern_path)
        box.pack_start(Align(text, border=3), True, True, 0)

        # cover image
        self.image = CoverImage(resize=True)
        connect_destroy(player, 'song-started', self.__new_song)

        # FIXME: makes testing easier
        if app.cover_manager:
            connect_destroy(app.cover_manager, 'cover-changed',
                            self.__song_art_changed, library)

        self.image.props.margin = 2
        box.pack_start(self.image, False, True, 0)

        for child in self.get_children():
            child.show_all()

        context = self.get_style_context()
        context.add_class("primary-toolbar")
Пример #20
0
    def __init__(self,
                 filename=None,
                 initial=[],
                 count=5,
                 id=None,
                 validator=None,
                 title=_("Saved Values"),
                 edit_title=_(u"Edit saved values…")):
        self.count = count
        self.filename = filename
        id = filename or id

        try:
            model = self.__models[id]
        except KeyError:
            model = type(self).__models[id] = Gtk.ListStore(str, str, str)

        super().__init__(model=model, entry_text_column=0, has_entry=True)
        self.clear()

        render = Gtk.CellRendererPixbuf()
        self.pack_start(render, False)
        self.add_attribute(render, 'icon-name', 2)

        render = Gtk.CellRendererText()
        self.pack_start(render, True)
        self.add_attribute(render, 'text', 1)

        self.set_row_separator_func(self.__separator_func, None)

        if not len(model):
            self.__fill(filename, initial, edit_title)

        old_entry = self.get_child()
        new_entry = entry.ValidatingEntry(validator)
        clone_css_classes(old_entry, new_entry)
        old_entry.destroy()
        use_mono = config.getboolean("settings", "monospace_query")
        font = "font-family: monospace; " if use_mono else ""
        size = escape(config.gettext("settings", "query_font_size"))
        add_css(new_entry, f"entry {{ {font} font-size: {size} }}")
        self.add(new_entry)
        if validator:
            # Call once more to ensure correct theme colours
            GLib.idle_add(new_entry._set_color, None, validator)

        connect_obj(self, 'destroy', self.set_model, None)
        connect_obj(self, 'changed', self.__changed, model, validator, title)
Пример #21
0
    def __init__(self):
        super(ReapeatButton, self).__init__(
            image=SymbolicIconImage(
                "media-playlist-repeat", Gtk.IconSize.SMALL_TOOLBAR))

        self.set_name("ql-repeat-button")
        qltk.add_css(self, """
            #ql-repeat-button {
                padding: 0px;
            }
        """)
        self.set_size_request(26, 26)

        self.set_tooltip_text(_("Restart the playlist when finished"))

        self.bind_config("settings", "repeat")
Пример #22
0
    def __init__(self):
        super(ReapeatButton, self).__init__(image=SymbolicIconImage(
            "media-playlist-repeat", Gtk.IconSize.SMALL_TOOLBAR))

        self.set_name("ql-repeat-button")
        qltk.add_css(
            self, """
            #ql-repeat-button {
                padding: 0px;
            }
        """)
        self.set_size_request(26, 26)

        self.set_tooltip_text(_("Restart the playlist when finished"))

        self.bind_config("settings", "repeat")
Пример #23
0
    def __init__(self, namespace=None, destroy_cb=None):
        Gtk.ScrolledWindow.__init__(self)

        self.destroy_cb = destroy_cb
        self.set_policy(Gtk.PolicyType.NEVER, Gtk.PolicyType.AUTOMATIC)
        self.set_shadow_type(Gtk.ShadowType.NONE)
        self.view = Gtk.TextView()
        add_css(
            self, "scrolledwindow { padding: 6px; "
            "background-color: white; background-color: @content_view_bg;}")
        self.view.modify_font(Pango.font_description_from_string('Monospace'))
        self.view.set_editable(True)
        self.view.set_wrap_mode(Gtk.WrapMode.CHAR)
        self.add(self.view)
        self.view.show()

        buffer = self.view.get_buffer()
        self.normal = buffer.create_tag("normal")
        self.error = buffer.create_tag("error")
        self.error.set_property("foreground", "red")
        self.command = buffer.create_tag("command")
        self.command.set_property("foreground", "blue")

        self.__spaces_pattern = re.compile(r'^\s+')
        self.namespace = namespace or {}

        self.block_command = False

        # Init first line
        buffer.create_mark("input-line", buffer.get_end_iter(), True)
        buffer.insert(buffer.get_end_iter(), ">>> ")
        buffer.create_mark("input", buffer.get_end_iter(), True)

        # Init history
        self.history = ['']
        self.history_pos = 0
        self.current_command = ''
        self.namespace['__history__'] = self.history

        # Set up hooks for standard output.
        self.stdout = OutFile(self, self.normal)
        self.stderr = OutFile(self, self.error)

        # Signals
        self.view.connect("key-press-event", self.__key_press_event_cb)
        buffer.connect("mark-set", self.__mark_set_cb)
Пример #24
0
    def __init__(self, parent, player, library):
        super(TopBar, self).__init__()

        # play controls
        control_item = Gtk.ToolItem()
        self.insert(control_item, 0)
        t = PlayControls(player, library.librarian)
        self.volume = t.volume
        control_item.add(t)

        self.insert(Gtk.SeparatorToolItem(), 1)

        info_item = Gtk.ToolItem()
        self.insert(info_item, 2)
        info_item.set_expand(True)

        box = Gtk.Box(spacing=6)
        info_item.add(box)
        qltk.add_css(self, "GtkToolbar {padding: 3px;}")

        # song text
        info_pattern_path = os.path.join(const.USERDIR, "songinfo")
        text = SongInfo(library.librarian, player, info_pattern_path)
        box.pack_start(Alignment(text, border=3), True, True, 0)

        # cover image
        self.image = CoverImage(resize=True)
        connect_destroy(player, 'song-started', self.__new_song)

        # FIXME: makes testing easier
        if app.cover_manager:
            connect_destroy(
                app.cover_manager, 'cover-changed',
                self.__song_art_changed, library)

        # CoverImage doesn't behave in a Alignment, so wrap it
        coverbox = Gtk.Box()
        coverbox.pack_start(self.image, True, True, 0)
        box.pack_start(Alignment(coverbox, border=2), False, True, 0)

        for child in self.get_children():
            child.show_all()

        context = self.get_style_context()
        context.add_class("primary-toolbar")
Пример #25
0
    def __init__(self):
        # XXX: view-list isn't part of the fdo spec, so fall back t justify..
        gicon = Gio.ThemedIcon.new_from_names(
            ["view-list-symbolic", "format-justify-fill-symbolic",
             "view-list", "format-justify"])
        image = Gtk.Image.new_from_gicon(gicon, Gtk.IconSize.SMALL_TOOLBAR)

        super(QueueButton, self).__init__(image=image)

        self.set_name("ql-queue-button")
        qltk.add_css(self, """
            #ql-queue-button {
                padding: 0px;
            }
        """)
        self.set_size_request(26, 26)

        self.set_tooltip_text(_("Toggle queue visibility"))
Пример #26
0
    def __init__(self, namespace=None, destroy_cb=None):
        Gtk.ScrolledWindow.__init__(self)

        self.destroy_cb = destroy_cb
        self.set_policy(Gtk.PolicyType.NEVER, Gtk.PolicyType.AUTOMATIC)
        self.set_shadow_type(Gtk.ShadowType.NONE)
        self.view = Gtk.TextView()
        add_css(self, "* { background-color: white; padding: 6px; } ")
        self.view.modify_font(Pango.font_description_from_string('Monospace'))
        self.view.set_editable(True)
        self.view.set_wrap_mode(Gtk.WrapMode.CHAR)
        self.add(self.view)
        self.view.show()

        buffer = self.view.get_buffer()
        self.normal = buffer.create_tag("normal")
        self.error = buffer.create_tag("error")
        self.error.set_property("foreground", "red")
        self.command = buffer.create_tag("command")
        self.command.set_property("foreground", "blue")

        self.__spaces_pattern = re.compile(r'^\s+')
        self.namespace = namespace or {}

        self.block_command = False

        # Init first line
        buffer.create_mark("input-line", buffer.get_end_iter(), True)
        buffer.insert(buffer.get_end_iter(), ">>> ")
        buffer.create_mark("input", buffer.get_end_iter(), True)

        # Init history
        self.history = ['']
        self.history_pos = 0
        self.current_command = ''
        self.namespace['__history__'] = self.history

        # Set up hooks for standard output.
        self.stdout = OutFile(self, self.normal)
        self.stderr = OutFile(self, self.error)

        # Signals
        self.view.connect("key-press-event", self.__key_press_event_cb)
        buffer.connect("mark-set", self.__mark_set_cb)
Пример #27
0
    def ensure_wide_handle(self):
        if hasattr(self.props, "wide_handle"):
            # gtk 3.16
            self.props.wide_handle = True
            add_css(self, """
                GtkPaned {
                    border-width: 0;
                }
            """)
            return

        # gtk 3.14
        add_css(self, """
            GtkPaned {
                -GtkPaned-handle-size: 6;
                background-image: none;
                margin: 0;
                border-width: 0;
            }
        """)
Пример #28
0
    def ensure_wide_handle(self):
        if hasattr(self.props, "wide_handle"):
            # gtk 3.16
            self.props.wide_handle = True
            add_css(self, """
                GtkPaned {
                    border-width: 0;
                }
            """)
            return

        # gtk 3.14
        add_css(self, """
            GtkPaned {
                -GtkPaned-handle-size: 6;
                background-image: none;
                margin: 0;
                border-width: 0;
            }
        """)
Пример #29
0
    def __init__(self, parent, player, library):
        super(TopBar, self).__init__()

        # play controls
        control_item = Gtk.ToolItem()
        self.insert(control_item, 0)
        t = PlayControls(player, library.librarian)
        self.volume = t.volume
        control_item.add(t)

        self.insert(Gtk.SeparatorToolItem(), 1)

        info_item = Gtk.ToolItem()
        self.insert(info_item, 2)
        info_item.set_expand(True)

        box = Gtk.Box(spacing=6)
        info_item.add(box)
        qltk.add_css(self, "GtkToolbar {padding: 3px;}")

        # song text
        text = SongInfo(library.librarian, player)
        box.pack_start(Alignment(text, border=3), True, True, 0)

        # cover image
        self.image = CoverImage(resize=True)
        gobject_weak(player.connect, 'song-started', self.__new_song,
                     parent=self)
        gobject_weak(parent.connect, 'artwork-changed',
                     self.__song_art_changed, library, parent=self)

        # CoverImage doesn't behave in a Alignment, so wrap it
        coverbox = Gtk.Box()
        coverbox.pack_start(self.image, True, True, 0)
        box.pack_start(Alignment(coverbox, border=2), False, True, 0)

        for child in self.get_children():
            child.show_all()

        context = self.get_style_context()
        context.add_class("primary-toolbar")
Пример #30
0
    def __init__(self, arrow_down=False):
        """arrow_down -- the direction of the menu and arrow icon"""

        super(ShuffleButton, self).__init__()

        context = self.get_style_context()
        context.add_class(Gtk.STYLE_CLASS_LINKED)

        # shuffle button
        b = Gtk.ToggleButton(image=SymbolicIconImage(
            "media-playlist-shuffle", Gtk.IconSize.SMALL_TOOLBAR))
        b.set_tooltip_text(_("Toggle shuffle mode"))
        b.show_all()
        qltk.add_css(
            b, """
            * {
                padding: 0px;
            }
        """)
        b.set_size_request(26, 26)
        self.pack_start(b, True, True, 0)

        def forward_signal(*args):
            self.emit("toggled")

        b.connect("toggled", forward_signal)
        self._toggle_button = b

        # arrow
        from quodlibet.qltk.menubutton import MenuButton
        b = MenuButton(arrow=True, down=arrow_down)
        b.show_all()
        b.set_size_request(20, 26)
        qltk.add_css(
            b, """
            * {
                padding: 0px;
            }
        """)
        self.pack_start(b, True, True, 0)
        self._menu_button = b
Пример #31
0
    def __init__(self, parent, rows):
        Gtk.Dialog.__init__(self,
                            title=_("Completion"),
                            transient_for=parent,
                            flags=0)
        self.set_default_size(400, 250)

        listbox = Gtk.ListBox()
        listbox.set_selection_mode(Gtk.SelectionMode.SINGLE)

        for i, (name, details) in enumerate(rows):
            row = Gtk.ListBoxRow()
            hbox = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL)
            row.add(hbox)

            lbl = Gtk.Label(label=name, xalign=0)
            lbl2 = Gtk.Label(label=details, xalign=0)
            hbox.pack_start(lbl, expand=False, fill=False, padding=0)
            hbox.pack_start(lbl2, expand=True, fill=True, padding=0)

            # dim the details-label
            style = lbl2.get_style_context()
            style.add_class('dim-label')
            add_css(lbl2, ".dim-label { opacity: 0.5; } ")

            listbox.add(row)

            if i == 0:
                listbox.set_focus_child(row)

        listbox.connect('row-activated', self.on_row_click)

        scroll = Gtk.ScrolledWindow()
        scroll.add(listbox)

        content = self.get_content_area()
        content.pack_start(scroll, True, True, 0)

        content.show_all()
        self.get_action_area().hide()
Пример #32
0
    def __init__(self, arrow_down=False):
        """arrow_down -- the direction of the menu and arrow icon"""

        super(ShuffleButton, self).__init__()

        context = self.get_style_context()
        context.add_class(Gtk.STYLE_CLASS_LINKED)

        # shuffle button
        b = Gtk.ToggleButton(image=SymbolicIconImage(
            "media-playlist-shuffle", Gtk.IconSize.SMALL_TOOLBAR))
        b.set_tooltip_text(_("Toggle shuffle mode"))
        b.show_all()
        qltk.add_css(b, """
            * {
                padding: 0px;
            }
        """)
        b.set_size_request(26, 26)
        self.pack_start(b, True, True, 0)

        def forward_signal(*args):
            self.emit("toggled")

        b.connect("toggled", forward_signal)
        self._toggle_button = b

        # arrow
        from quodlibet.qltk.menubutton import MenuButton
        b = MenuButton(arrow=True, down=arrow_down)
        b.show_all()
        b.set_size_request(20, 26)
        qltk.add_css(b, """
            * {
                padding: 0px;
            }
        """)
        self.pack_start(b, True, True, 0)
        self._menu_button = b
Пример #33
0
    def __init__(self, library, player):
        super().__init__(spacing=3)
        sw = ScrolledWindow()
        sw.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC)
        sw.set_shadow_type(Gtk.ShadowType.IN)
        save_interval_secs = config.getint("autosave", "queue_interval")
        self.queue = PlayQueue(library, player, save_interval_secs)
        self.queue.props.expand = True
        sw.add(self.queue)

        add_css(self, ".ql-expanded title { margin-bottom: 5px; }")

        outer = ExpandBoxHack()

        left = Gtk.HBox(spacing=12)

        hb2 = Gtk.HBox(spacing=3)
        state_icon = PlaybackStatusIcon()
        state_icon.stop()
        state_icon.show()
        hb2.pack_start(state_icon, True, True, 0)
        name_label = Gtk.Label(label=_("_Queue"), use_underline=True)
        name_label.set_size_request(-1, 24)
        hb2.pack_start(name_label, True, True, 0)
        left.pack_start(hb2, False, True, 0)

        menu = Gtk.Menu()

        self.count_label = count_label = Gtk.Label()
        self.count_label.set_property("ellipsize", Pango.EllipsizeMode.END)
        self.count_label.set_width_chars(10)
        self.count_label.get_style_context().add_class("dim-label")
        left.pack_start(count_label, False, True, 0)

        outer.pack_start(left, True, True, 0)

        self.set_label_fill(True)

        clear_item = SmallImageButton(image=SymbolicIconImage(
            Icons.USER_TRASH, Gtk.IconSize.MENU),
                                      relief=Gtk.ReliefStyle.NONE,
                                      tooltip_text=_("Clear Queue"))
        clear_item.connect("clicked", self.__clear_queue)
        outer.pack_start(clear_item, False, False, 3)

        toggle = SmallImageToggleButton(
            image=SymbolicIconImage(Icons.SYSTEM_LOCK_SCREEN,
                                    Gtk.IconSize.MENU),
            relief=Gtk.ReliefStyle.NONE,
            tooltip_text=_(
                "Disable queue - the queue will be ignored when playing"))
        disabled = config.getboolean("memory", "queue_disable", False)
        toggle.props.active = disabled
        self.__queue_disable(disabled)
        toggle.connect('toggled',
                       lambda b: self.__queue_disable(b.props.active))
        outer.pack_start(toggle, False, False, 3)

        mode_menu = Gtk.Menu()

        norm_mode_item = RadioMenuItem(
            label=_("Ephemeral"),
            tooltip_text=_("Remove songs from the queue after playing them"),
            group=None)
        mode_menu.append(norm_mode_item)
        norm_mode_item.set_active(True)
        norm_mode_item.connect("toggled",
                               lambda _: self.__keep_songs_enable(False))

        keep_mode_item = RadioMenuItem(
            label=_("Persistent"),
            tooltip_text=_("Keep songs in the queue after playing them"),
            group=norm_mode_item)
        mode_menu.append(keep_mode_item)
        keep_mode_item.connect("toggled",
                               lambda b: self.__keep_songs_enable(True))
        keep_mode_item.set_active(
            config.getboolean("memory", "queue_keep_songs", False))

        mode_item = MenuItem(_("Mode"), Icons.SYSTEM_RUN)
        mode_item.set_submenu(mode_menu)
        menu.append(mode_item)

        rand_checkbox = ConfigCheckMenuItem(_("_Random"),
                                            "memory",
                                            "shufflequeue",
                                            populate=True)
        rand_checkbox.connect('toggled', self.__queue_shuffle)
        self.set_shuffled(rand_checkbox.get_active())
        menu.append(rand_checkbox)

        stop_checkbox = ConfigCheckMenuItem(_("Stop at End"),
                                            "memory",
                                            "queue_stop_at_end",
                                            populate=True)
        menu.append(stop_checkbox)

        button = SmallMenuButton(SymbolicIconImage(Icons.EMBLEM_SYSTEM,
                                                   Gtk.IconSize.MENU),
                                 arrow=True)
        button.set_relief(Gtk.ReliefStyle.NORMAL)
        button.show_all()
        button.hide()
        button.set_no_show_all(True)
        menu.show_all()
        button.set_menu(menu)

        outer.pack_start(button, False, False, 3)

        close_button = SmallImageButton(image=SymbolicIconImage(
            "window-close", Gtk.IconSize.MENU),
                                        relief=Gtk.ReliefStyle.NONE)

        close_button.connect("clicked", lambda *x: self.hide())

        outer.pack_start(close_button, False, False, 6)

        self.set_label_widget(outer)
        self.add(sw)
        self.connect('notify::expanded', self.__expand, button)
        self.connect('notify::expanded', self.__expand, button)

        targets = [("text/x-quodlibet-songs", Gtk.TargetFlags.SAME_APP,
                    DND_QL), ("text/uri-list", 0, DND_URI_LIST)]
        targets = [Gtk.TargetEntry.new(*t) for t in targets]

        self.drag_dest_set(Gtk.DestDefaults.ALL, targets, Gdk.DragAction.COPY)
        self.connect('drag-motion', self.__motion)
        self.connect('drag-data-received', self.__drag_data_received)

        self.queue.model.connect_after('row-inserted',
                                       DeferredSignal(self.__check_expand),
                                       count_label)
        self.queue.model.connect_after('row-deleted',
                                       DeferredSignal(self.__update_count),
                                       count_label)

        self.__update_count(self.model, None, count_label)

        connect_destroy(player, 'song-started', self.__update_state_icon,
                        state_icon)
        connect_destroy(player, 'paused', self.__update_state_icon_pause,
                        state_icon, True)
        connect_destroy(player, 'unpaused', self.__update_state_icon_pause,
                        state_icon, False)

        connect_destroy(player, 'song-started', self.__song_started,
                        self.queue.model)
        connect_destroy(player, 'song-ended', self.__update_queue_stop,
                        self.queue.model)

        # to make the children clickable if mapped
        # ....no idea why, but works
        def hack(expander):
            label = expander.get_label_widget()
            if label:
                label.unmap()
                label.map()

        self.connect("map", hack)

        self.set_expanded(config.getboolean("memory", "queue_expanded"))
        self.notify("expanded")

        for child in self.get_children():
            child.show_all()
Пример #34
0
    def draw_title_info(self, cr):
        cr.save()
        do_shadow = (self.conf.shadow[0] != -1.0)
        do_outline = (self.conf.outline[0] != -1.0)

        self.set_name("osd_bubble")
        qltk.add_css(
            self, """
            #osd_bubble {
                background-color:rgba(0,0,0,0);
            }
        """)

        cr.set_operator(cairo.OPERATOR_OVER)
        cr.set_source_rgba(*self.conf.fill)
        radius = min(25, self.corners_factor * min(*self.get_size()))
        self.draw_conf_rect(cr, 0, 0,
                            self.get_size()[0],
                            self.get_size()[1], radius)
        cr.fill()

        # draw border
        if do_outline:
            # Make border darker and more translucent than the fill
            f = self.conf.fill
            rgba = (f[0] / 1.25, f[1] / 1.25, f[2] / 1.25, f[3] / 2.0)
            cr.set_source_rgba(*rgba)
            self.draw_conf_rect(cr, 1, 1,
                                self.get_size()[0] - 2,
                                self.get_size()[1] - 2, radius)
            cr.set_line_width(2.0)
            cr.stroke()

        textx = self.BORDER

        if self.cover_pixbuf is not None:
            rect = self.cover_rectangle
            textx += rect.width + self.BORDER
            pbuf = self.cover_pixbuf
            transmat = cairo.Matrix()

            if do_shadow:
                cr.set_source_rgba(*self.conf.shadow)
                self.draw_conf_rect(cr, rect.x + 2, rect.y + 2, rect.width,
                                    rect.height,
                                    0.6 * self.corners_factor * rect.width)
                cr.fill()

            if do_outline:
                cr.set_source_rgba(*self.conf.outline)
                self.draw_conf_rect(cr, rect.x, rect.y, rect.width,
                                    rect.height,
                                    0.6 * self.corners_factor * rect.width)
                cr.stroke()

            set_ctx_source_from_pbosf(cr, pbuf)
            transmat.scale(
                pbosf_get_width(pbuf) / float(rect.width),
                pbosf_get_height(pbuf) / float(rect.height))
            transmat.translate(-rect.x, -rect.y)
            cr.get_source().set_matrix(transmat)
            self.draw_conf_rect(cr, rect.x, rect.y, rect.width, rect.height,
                                0.6 * self.corners_factor * rect.width)
            cr.fill()

        PangoCairo.update_layout(cr, self.title_layout)
        height = self.title_layout.get_pixel_size()[1]
        texty = (self.get_size()[1] - height) // 2

        if do_shadow:
            cr.set_source_rgba(*self.conf.shadow)
            cr.move_to(textx + 2, texty + 2)
            PangoCairo.show_layout(cr, self.title_layout)
        if do_outline:
            cr.set_source_rgba(*self.conf.outline)
            cr.move_to(textx, texty)
            PangoCairo.layout_path(cr, self.title_layout)
            cr.stroke()
        cr.set_source_rgb(*self.conf.text[:3])
        cr.move_to(textx, texty)
        PangoCairo.show_layout(cr, self.title_layout)
        cr.restore()
Пример #35
0
    def __init__(self, library, player):
        super(QueueExpander, self).__init__(spacing=3)
        sw = ScrolledWindow()
        sw.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC)
        sw.set_shadow_type(Gtk.ShadowType.IN)
        self.queue = PlayQueue(library, player)
        self.queue.props.expand = True
        sw.add(self.queue)

        add_css(self, ".ql-expanded title { margin-bottom: 5px; }")

        outer = ExpandBoxHack()

        left = Gtk.HBox(spacing=12)

        hb2 = Gtk.HBox(spacing=3)
        state_icon = PlaybackStatusIcon()
        state_icon.stop()
        state_icon.show()
        hb2.pack_start(state_icon, True, True, 0)
        name_label = Gtk.Label(label=_("_Queue"), use_underline=True)
        name_label.set_size_request(-1, 24)
        hb2.pack_start(name_label, True, True, 0)
        left.pack_start(hb2, False, True, 0)

        menu = Gtk.Menu()

        self.count_label = count_label = Gtk.Label()
        self.count_label.set_property("ellipsize", Pango.EllipsizeMode.END)
        self.count_label.set_width_chars(10)
        self.count_label.get_style_context().add_class("dim-label")
        left.pack_start(count_label, False, True, 0)

        outer.pack_start(left, True, True, 0)

        self.set_label_fill(True)

        rand_checkbox = ConfigCheckMenuItem(
                _("_Random"), "memory", "shufflequeue", populate=True)
        rand_checkbox.connect('toggled', self.__queue_shuffle)
        self.set_shuffled(rand_checkbox.get_active())
        menu.append(rand_checkbox)

        stop_checkbox = ConfigCheckMenuItem(
            _("Stop Once Empty"), "memory", "queue_stop_once_empty",
            populate=True)
        menu.append(stop_checkbox)

        clear_item = MenuItem(_("_Clear Queue"), Icons.EDIT_CLEAR)
        menu.append(clear_item)
        clear_item.connect("activate", self.__clear_queue)

        button = SmallMenuButton(
            SymbolicIconImage(Icons.EMBLEM_SYSTEM, Gtk.IconSize.MENU),
            arrow=True)
        button.set_relief(Gtk.ReliefStyle.NONE)
        button.show_all()
        button.hide()
        button.set_no_show_all(True)
        menu.show_all()
        button.set_menu(menu)

        outer.pack_start(button, False, False, 0)

        close_button = SmallImageButton(
            image=SymbolicIconImage("window-close", Gtk.IconSize.MENU),
            relief=Gtk.ReliefStyle.NONE)

        close_button.connect("clicked", lambda *x: self.hide())

        outer.pack_start(close_button, False, False, 6)

        self.set_label_widget(outer)
        self.add(sw)
        self.connect('notify::expanded', self.__expand, button)
        self.connect('notify::expanded', self.__expand, button)

        targets = [
            ("text/x-quodlibet-songs", Gtk.TargetFlags.SAME_APP, DND_QL),
            ("text/uri-list", 0, DND_URI_LIST)
        ]
        targets = [Gtk.TargetEntry.new(*t) for t in targets]

        self.drag_dest_set(Gtk.DestDefaults.ALL, targets, Gdk.DragAction.COPY)
        self.connect('drag-motion', self.__motion)
        self.connect('drag-data-received', self.__drag_data_received)

        self.queue.model.connect_after('row-inserted',
            util.DeferredSignal(self.__check_expand), count_label)
        self.queue.model.connect_after('row-deleted',
            util.DeferredSignal(self.__update_count), count_label)

        self.__update_count(self.model, None, count_label)

        connect_destroy(
            player, 'song-started', self.__update_state_icon, state_icon)
        connect_destroy(
            player, 'paused', self.__update_state_icon_pause,
            state_icon, True)
        connect_destroy(
            player, 'unpaused', self.__update_state_icon_pause,
            state_icon, False)

        connect_destroy(
            player, 'song-started', self.__song_started, self.queue.model)
        connect_destroy(
            player, 'song-ended', self.__update_queue_stop, self.queue.model)

        self._last_queue_song = None

        # to make the children clickable if mapped
        # ....no idea why, but works
        def hack(expander):
            label = expander.get_label_widget()
            if label:
                label.unmap()
                label.map()
        self.connect("map", hack)

        self.set_expanded(config.getboolean("memory", "queue_expanded"))
        self.notify("expanded")

        for child in self.get_children():
            child.show_all()
Пример #36
0
    def __init__(self, library, player):
        super(QueueExpander, self).__init__(spacing=3)
        sw = ScrolledWindow()
        sw.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC)
        sw.set_shadow_type(Gtk.ShadowType.IN)
        self.queue = PlayQueue(library, player)
        self.queue.props.expand = True
        sw.add(self.queue)

        add_css(self, ".ql-expanded title { margin-bottom: 5px; }")

        outer = ExpandBoxHack()

        left = Gtk.HBox(spacing=12)

        hb2 = Gtk.HBox(spacing=3)
        state_icon = PlaybackStatusIcon()
        state_icon.stop()
        state_icon.show()
        hb2.pack_start(state_icon, True, True, 0)
        name_label = Gtk.Label(label=_("_Queue"), use_underline=True)
        name_label.set_size_request(-1, 24)
        hb2.pack_start(name_label, True, True, 0)
        left.pack_start(hb2, False, True, 0)

        menu = Gtk.Menu()

        self.count_label = count_label = Gtk.Label()
        self.count_label.set_property("ellipsize", Pango.EllipsizeMode.END)
        self.count_label.set_width_chars(10)
        self.count_label.get_style_context().add_class("dim-label")
        left.pack_start(count_label, False, True, 0)

        outer.pack_start(left, True, True, 0)

        self.set_label_fill(True)

        rand_checkbox = ConfigCheckMenuItem(
                _("_Random"), "memory", "shufflequeue", populate=True)
        rand_checkbox.connect('toggled', self.__queue_shuffle)
        self.set_shuffled(rand_checkbox.get_active())
        menu.append(rand_checkbox)

        stop_checkbox = ConfigCheckMenuItem(
            _("Stop Once Empty"), "memory", "queue_stop_once_empty",
            populate=True)
        menu.append(stop_checkbox)

        clear_item = MenuItem(_("_Clear Queue"), Icons.EDIT_CLEAR)
        menu.append(clear_item)
        clear_item.connect("activate", self.__clear_queue)

        button = SmallMenuButton(
            SymbolicIconImage(Icons.EMBLEM_SYSTEM, Gtk.IconSize.MENU),
            arrow=True)
        button.set_relief(Gtk.ReliefStyle.NONE)
        button.show_all()
        button.hide()
        button.set_no_show_all(True)
        menu.show_all()
        button.set_menu(menu)

        outer.pack_start(button, False, False, 0)

        close_button = SmallImageButton(
            image=SymbolicIconImage("window-close", Gtk.IconSize.MENU),
            relief=Gtk.ReliefStyle.NONE)

        close_button.connect("clicked", lambda *x: self.hide())

        outer.pack_start(close_button, False, False, 6)

        self.set_label_widget(outer)
        self.add(sw)
        self.connect('notify::expanded', self.__expand, button)
        self.connect('notify::expanded', self.__expand, button)

        targets = [
            ("text/x-quodlibet-songs", Gtk.TargetFlags.SAME_APP, DND_QL),
            ("text/uri-list", 0, DND_URI_LIST)
        ]
        targets = [Gtk.TargetEntry.new(*t) for t in targets]

        self.drag_dest_set(Gtk.DestDefaults.ALL, targets, Gdk.DragAction.COPY)
        self.connect('drag-motion', self.__motion)
        self.connect('drag-data-received', self.__drag_data_received)

        self.queue.model.connect_after('row-inserted',
            util.DeferredSignal(self.__check_expand), count_label)
        self.queue.model.connect_after('row-deleted',
            util.DeferredSignal(self.__update_count), count_label)

        self.__update_count(self.model, None, count_label)

        connect_destroy(
            player, 'song-started', self.__update_state_icon, state_icon)
        connect_destroy(
            player, 'paused', self.__update_state_icon_pause,
            state_icon, True)
        connect_destroy(
            player, 'unpaused', self.__update_state_icon_pause,
            state_icon, False)

        connect_destroy(
            player, 'song-started', self.__update_queue_stop, self.queue.model)

        # to make the children clickable if mapped
        # ....no idea why, but works
        def hack(expander):
            label = expander.get_label_widget()
            if label:
                label.unmap()
                label.map()
        self.connect("map", hack)

        self.set_expanded(config.getboolean("memory", "queue_expanded"))
        self.notify("expanded")

        for child in self.get_children():
            child.show_all()
Пример #37
0
    def __init__(self, library, player):
        super(QueueExpander, self).__init__(spacing=3)
        sw = ScrolledWindow()
        sw.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC)
        sw.set_shadow_type(Gtk.ShadowType.IN)
        self.queue = PlayQueue(library, player)
        self.queue.props.expand = True
        sw.add(self.queue)

        add_css(self, ".ql-expanded title { margin-bottom: 5px; }")

        outer = ExpandBoxHack(spacing=12)

        left = Gtk.HBox(spacing=12)

        hb2 = Gtk.HBox(spacing=3)
        state_icon = PlaybackStatusIcon()
        state_icon.stop()
        state_icon.show()
        hb2.pack_start(state_icon, True, True, 0)
        name_label = Gtk.Label(label=_("_Queue"), use_underline=True)
        hb2.pack_start(name_label, True, True, 0)
        left.pack_start(hb2, False, True, 0)

        b = SmallImageButton(
            image=SymbolicIconImage(Icons.EDIT_CLEAR, Gtk.IconSize.MENU))
        b.set_tooltip_text(_("Remove all songs from the queue"))
        b.connect('clicked', self.__clear_queue)
        b.set_no_show_all(True)
        b.set_relief(Gtk.ReliefStyle.NONE)
        left.pack_start(b, False, False, 0)

        self.count_label = count_label = Gtk.Label()
        left.pack_start(count_label, False, True, 0)

        outer.pack_start(left, True, True, 0)

        close_button = SmallImageButton(
            image=SymbolicIconImage("window-close", Gtk.IconSize.MENU),
            relief=Gtk.ReliefStyle.NONE)

        close_button.connect("clicked", lambda *x: self.hide())

        outer.pack_start(close_button, False, False, 6)
        self.set_label_fill(True)

        cb = ConfigCheckButton(
            _("_Random"), "memory", "shufflequeue")
        cb.connect('toggled', self.__queue_shuffle, self.queue.model)
        cb.set_active(config.getboolean("memory", "shufflequeue"))
        cb.set_no_show_all(True)
        left.pack_start(cb, False, True, 0)

        self.set_label_widget(outer)
        self.add(sw)
        connect_obj(self, 'notify::expanded', self.__expand, cb, b)

        targets = [
            ("text/x-quodlibet-songs", Gtk.TargetFlags.SAME_APP, DND_QL),
            ("text/uri-list", 0, DND_URI_LIST)
        ]
        targets = [Gtk.TargetEntry.new(*t) for t in targets]

        self.drag_dest_set(Gtk.DestDefaults.ALL, targets, Gdk.DragAction.COPY)
        self.connect('drag-motion', self.__motion)
        self.connect('drag-data-received', self.__drag_data_received)

        self.queue.model.connect_after('row-inserted',
            util.DeferredSignal(self.__check_expand), count_label)
        self.queue.model.connect_after('row-deleted',
            util.DeferredSignal(self.__update_count), count_label)

        connect_obj(self, 'notify::visible', self.__visible, cb, b)
        self.__update_count(self.model, None, count_label)

        connect_destroy(
            player, 'song-started', self.__update_state_icon, state_icon)
        connect_destroy(
            player, 'paused', self.__update_state_icon_pause,
            state_icon, True)
        connect_destroy(
            player, 'unpaused', self.__update_state_icon_pause,
            state_icon, False)

        # to make the children clickable if mapped
        # ....no idea why, but works
        def hack(expander):
            label = expander.get_label_widget()
            if label:
                label.unmap()
                label.map()
        self.connect("map", hack)

        self.set_expanded(config.getboolean("memory", "queue_expanded"))
        self.notify("expanded")

        for child in self.get_children():
            child.show_all()
Пример #38
0
    def __init__(self, library, player):
        super(QueueExpander, self).__init__(spacing=3)
        sw = ScrolledWindow()
        sw.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC)
        sw.set_shadow_type(Gtk.ShadowType.IN)
        self.queue = PlayQueue(library, player)
        self.queue.props.expand = True
        sw.add(self.queue)

        add_css(self, ".ql-expanded title { margin-bottom: 5px; }")

        outer = ExpandBoxHack(spacing=12)

        left = Gtk.HBox(spacing=12)

        hb2 = Gtk.HBox(spacing=3)
        state_icon = PlaybackStatusIcon()
        state_icon.stop()
        state_icon.show()
        hb2.pack_start(state_icon, True, True, 0)
        name_label = Gtk.Label(label=_("_Queue"), use_underline=True)
        hb2.pack_start(name_label, True, True, 0)
        left.pack_start(hb2, False, True, 0)

        b = SmallImageButton(
            image=SymbolicIconImage(Icons.EDIT_CLEAR, Gtk.IconSize.MENU))
        b.set_tooltip_text(_("Remove all songs from the queue"))
        b.connect('clicked', self.__clear_queue)
        b.set_no_show_all(True)
        b.set_relief(Gtk.ReliefStyle.NONE)
        left.pack_start(b, False, False, 0)

        count_label = Gtk.Label()
        left.pack_start(count_label, False, True, 0)

        outer.pack_start(left, True, True, 0)

        close_button = SmallImageButton(image=SymbolicIconImage(
            "window-close", Gtk.IconSize.MENU),
                                        relief=Gtk.ReliefStyle.NONE)

        close_button.connect("clicked", lambda *x: self.hide())

        outer.pack_start(close_button, False, False, 6)
        self.set_label_fill(True)

        cb = ConfigCheckButton(_("_Random"), "memory", "shufflequeue")
        cb.connect('toggled', self.__queue_shuffle, self.queue.model)
        cb.set_active(config.getboolean("memory", "shufflequeue"))
        cb.set_no_show_all(True)
        left.pack_start(cb, False, True, 0)

        self.set_label_widget(outer)
        self.add(sw)
        connect_obj(self, 'notify::expanded', self.__expand, cb, b)

        targets = [("text/x-quodlibet-songs", Gtk.TargetFlags.SAME_APP,
                    DND_QL), ("text/uri-list", 0, DND_URI_LIST)]
        targets = [Gtk.TargetEntry.new(*t) for t in targets]

        self.drag_dest_set(Gtk.DestDefaults.ALL, targets, Gdk.DragAction.COPY)
        self.connect('drag-motion', self.__motion)
        self.connect('drag-data-received', self.__drag_data_received)

        self.queue.model.connect_after(
            'row-inserted', util.DeferredSignal(self.__check_expand),
            count_label)
        self.queue.model.connect_after(
            'row-deleted', util.DeferredSignal(self.__update_count),
            count_label)

        connect_obj(self, 'notify::visible', self.__visible, cb, b)
        self.__update_count(self.model, None, count_label)

        connect_destroy(player, 'song-started', self.__update_state_icon,
                        state_icon)
        connect_destroy(player, 'paused', self.__update_state_icon_pause,
                        state_icon, True)
        connect_destroy(player, 'unpaused', self.__update_state_icon_pause,
                        state_icon, False)

        # to make the children clickable if mapped
        # ....no idea why, but works
        def hack(expander):
            label = expander.get_label_widget()
            if label:
                label.unmap()
                label.map()

        self.connect("map", hack)

        self.set_expanded(config.getboolean("memory", "queue_expanded"))
        self.notify("expanded")

        for child in self.get_children():
            child.show_all()
Пример #39
0
    def draw_title_info(self, cr):
        cr.save()
        do_shadow = (self.conf.shadow[0] != -1.0)
        do_outline = (self.conf.outline[0] != -1.0)

        self.set_name("osd_bubble")
        qltk.add_css(self, """
            #osd_bubble {
                background-color:rgba(0,0,0,0);
            }
        """)

        cr.set_operator(cairo.OPERATOR_OVER)
        cr.set_source_rgba(*self.conf.fill)
        radius = min(25, self.corners_factor * min(*self.get_size()))
        self.draw_conf_rect(cr, 0, 0, self.get_size()[0],
                            self.get_size()[1], radius)
        cr.fill()

        # draw border
        if do_outline:
            # Make border darker and more translucent than the fill
            f = self.conf.fill
            rgba = (f[0] / 1.25, f[1] / 1.25, f[2] / 1.25, f[3] / 2.0)
            cr.set_source_rgba(*rgba)
            self.draw_conf_rect(cr,
                                1, 1,
                                self.get_size()[0] - 2, self.get_size()[1] - 2,
                                radius)
            cr.set_line_width(2.0)
            cr.stroke()

        textx = self.BORDER

        if self.cover_pixbuf is not None:
            rect = self.cover_rectangle
            textx += rect.width + self.BORDER
            pbuf = self.cover_pixbuf
            transmat = cairo.Matrix()

            if do_shadow:
                cr.set_source_rgba(*self.conf.shadow)
                self.draw_conf_rect(cr,
                                    rect.x + 2, rect.y + 2,
                                    rect.width, rect.height,
                                    0.6 * self.corners_factor * rect.width)
                cr.fill()

            if do_outline:
                cr.set_source_rgba(*self.conf.outline)
                self.draw_conf_rect(cr,
                                    rect.x, rect.y,
                                    rect.width, rect.height,
                                    0.6 * self.corners_factor * rect.width)
                cr.stroke()

            set_ctx_source_from_pbosf(cr, pbuf)
            transmat.scale(pbosf_get_width(pbuf) / float(rect.width),
                           pbosf_get_height(pbuf) / float(rect.height))
            transmat.translate(-rect.x, -rect.y)
            cr.get_source().set_matrix(transmat)
            self.draw_conf_rect(cr,
                                rect.x, rect.y,
                                rect.width, rect.height,
                                0.6 * self.corners_factor * rect.width)
            cr.fill()

        PangoCairo.update_layout(cr, self.title_layout)
        height = self.title_layout.get_pixel_size()[1]
        texty = (self.get_size()[1] - height) // 2

        if do_shadow:
            cr.set_source_rgba(*self.conf.shadow)
            cr.move_to(textx + 2, texty + 2)
            PangoCairo.show_layout(cr, self.title_layout)
        if do_outline:
            cr.set_source_rgba(*self.conf.outline)
            cr.move_to(textx, texty)
            PangoCairo.layout_path(cr, self.title_layout)
            cr.stroke()
        cr.set_source_rgb(*self.conf.text[:3])
        cr.move_to(textx, texty)
        PangoCairo.show_layout(cr, self.title_layout)
        cr.restore()