class gimpPaletteExporter:

    def __init__(self, name):
        # We want people to select a palette and a location to save to...
        self.fileName = QFileDialog.getExistingDirectory()
        allPalettes = Application.resources("palette")
        self.paletteName = name
        self.currentPalette = Palette(allPalettes[self.paletteName])
        self.export()
        done = QMessageBox()
        done.setWindowTitle(i18n("Export Successful"))
        done.setText(
            str(i18n("{input} has been exported to {output}.")).format(
                input=self.paletteName, output=self.fileName))
        done.exec_()
        pass

    def export(self):
        # open the appropriate file...
        gplFile = open(self.fileName + "/" + self.paletteName + ".gpl", "w")
        gplFile.write("GIMP Palette\n")
        gplFile.write("Name: %s\n" % self.paletteName)
        gplFile.write("Columns: %s/n", self.currentPalette.columnCount())
        gplFile.write("#%s\n" % self.currentPalette.comment())
        colorCount = self.currentPalette.colorsCountGroup("")

        for i in range(colorCount):
            entry = self.currentPalette.colorSetEntryFromGroup(i, "")
            color = self.currentPalette.colorForEntry(entry)
            # convert to sRGB
            color.setColorSpace("RGBA", "U8", "sRGB built-in")

            red = max(min(int(color.componentsOrdered()[0] * 255), 255), 0)
            green = max(min(int(color.componentsOrdered()[1] * 255), 255), 0)
            blue = max(min(int(color.componentsOrdered()[2] * 255), 255), 0)
            gplFile.write(
                "{red} {green} {blue}    {id}-{name}\n".format(
                    red=red, green=green, blue=blue, id=entry.id(),
                    name=entry.name))
            groupNames = self.currentPalette.groupNames()
            for groupName in groupNames:
                colorCount = self.currentPalette.colorsCountGroup(groupName)
                for i in range(colorCount):
                    entry = self.currentPalette.colorSetEntryFromGroup(
                        i, groupName)
                    color = self.currentPalette.colorForEntry(entry)
                    # convert to sRGB
                    color.setColorSpace("RGBA", "U8", "sRGB built-in")
                    red = max(
                        min(int(color.componentsOrdered()[0] * 255), 255), 0)
                    green = max(
                        min(int(color.componentsOrdered()[1] * 255), 255), 0)
                    blue = max(
                        min(int(color.componentsOrdered()[2] * 255), 255), 0)
                    gplFile.write(
                        "{red} {green} {blue}    {id}-{name}\n".format(
                            red=red, green=green, blue=blue, id=entry.id(),
                            name=entry.name))
        gplFile.close()
Exemple #2
0
class sortColors(object):
    def __init__(self, name):
        # We want people to select a palette...
        allPalettes = Application.resources("palette")
        self.paletteName = name
        self.currentPalette = Palette(allPalettes[self.paletteName])
        self.sort_all_groups()

    def sort_all_groups(self):
        self.sort_color_by_name(str())
        groupNames = self.currentPalette.groupNames()
        for groupName in groupNames:
            self.sort_color_by_name(groupName)

    def sort_color_by_name(self, groupName):
        d = {}
        colorCount = self.currentPalette.colorsCountGroup(groupName)
        for i in range(colorCount - 1, -1, -1):
            entry = self.currentPalette.colorSetEntryFromGroup((i), groupName)
            d[entry.name + str(i)] = entry
            self.currentPalette.removeEntry((i), groupName)

        for s in sorted(d):
            self.currentPalette.addEntry(d[s], groupName)

    def sort_color_by_id(self, groupName):
        d = {}
        colorCount = self.currentPalette.colorsCountGroup(groupName)
        for i in range(colorCount - 1, -1, -1):
            entry = self.currentPalette.colorSetEntryFromGroup((i), groupName)
            d[entry.id() + " " + str(i)] = entry
            self.currentPalette.removeEntry((i), groupName)

        for s in sorted(d):
            self.currentPalette.addEntry(d[s], groupName)

    def sort_by_value(self, groupName):
        d = {}
        colorCount = self.currentPalette.colorsCountGroup(groupName)
        for i in range(colorCount - 1, -1, -1):
            entry = self.currentPalette.colorSetEntryFromGroup((i), groupName)
            color = self.currentPalette.colorForEntry(entry)
            color.setColorSpace("RGBA", "U8", "sRGB built-in")
            d[color.components()[0] + color.components()[1] +
              color.components()[2]] = entry
            self.currentPalette.removeEntry((i), groupName)

        for s in sorted(d):
            self.currentPalette.addEntry(d[s], groupName)

    def sort_by_hue(self, stepsize, groupName):
        pass

    def palette(self):
        return self.currentPalette
class inkscapeSVGExporter:
    def __init__(self, name):
        # We want people to select a palette and a location to save to...
        self.fileName = QFileDialog.getExistingDirectory()
        allPalettes = Application.resources("palette")
        self.paletteName = name
        self.currentPalette = Palette(allPalettes[self.paletteName])
        self.export()
        done = QMessageBox()
        done.setWindowTitle(i18n("Export Successful"))
        done.setText(
            str(i18n("{input} has been exported to {output}.")).format(
                input=self.paletteName, output=self.fileName))
        done.exec_()
        pass

    def export(self):
        # open the appropriate file...
        svgFile = open(self.fileName + "/" + self.paletteName + ".svg", "w")
        svgDoc = QDomDocument()
        svgBaseElement = svgDoc.createElement("svg")
        svgBaseElement.setAttribute(
            "xmlns:osb", "http://www.openswatchbook.org/uri/2009/osb")
        svgBaseElement.setAttribute("xmlns:svg", "http://www.w3.org/2000/svg")
        svgBaseElement.setAttribute("xmlns:dc",
                                    "http://purl.org/dc/elements/1.1/")
        svgBaseElement.setAttribute("xmlns:cc",
                                    "http://creativecommons.org/ns#")
        svgBaseElement.setAttribute(
            "xmlns:rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#")
        svgDefs = svgDoc.createElement("defs")
        svgSwatches = svgDoc.createElement("g")
        svgSwatches.setAttribute("id", "Swatches")

        svgMeta = svgDoc.createElement("metadata")
        svgBaseElement.appendChild(svgMeta)
        rdf = svgDoc.createElement("rdf:RDF")
        ccwork = svgDoc.createElement("cc:Work")
        dctitle = svgDoc.createElement("dc:title")
        dcdescription = svgDoc.createElement("dc:description")
        dctitle.appendChild(svgDoc.createTextNode(self.paletteName))
        dcdescription.appendChild(
            svgDoc.createTextNode(self.currentPalette.comment()))
        ccwork.appendChild(dctitle)
        ccwork.appendChild(dcdescription)
        rdf.appendChild(ccwork)
        svgMeta.appendChild(rdf)
        Row = 0
        Column = 0
        iccProfileList = []

        colorCount = self.currentPalette.colorsCountGroup("")

        for i in range(colorCount):
            entry = self.currentPalette.colorSetEntryFromGroup(i, "")
            color = self.currentPalette.colorForEntry(entry)

            iccColor = "icc-color(" + color.colorProfile()
            for c in range(len(color.componentsOrdered()) - 1):
                iccColor = "{col},{c}".format(col=iccColor,
                                              c=color.componentsOrdered()[c])
            iccColor = iccColor + ")"
            if color.colorProfile() not in iccProfileList:
                iccProfileList.append(color.colorProfile())

            # convert to sRGB
            color.setColorSpace("RGBA", "U8", "sRGB built-in")
            red = max(min(int(color.componentsOrdered()[0] * 255), 255), 0)
            green = max(min(int(color.componentsOrdered()[1] * 255), 255), 0)
            blue = max(min(int(color.componentsOrdered()[2] * 255), 255), 0)
            hexcode = "#{red:02x}{green:02x}{blue:02x}".format(red=red,
                                                               green=green,
                                                               blue=blue)
            swatchName = "{i}-{name}".format(i=i, name=entry.name())
            swatchName = swatchName.replace(" ", "-")
            swatchName = swatchName.replace("(", "-")
            swatchName = swatchName.replace(")", "-")
            swatchMain = svgDoc.createElement("linearGradient")
            swatchMain.setAttribute("osb:paint", "solid")
            swatchMain.setAttribute("id", swatchName)
            swatchSub = svgDoc.createElement("stop")
            swatchSub.setAttribute(
                "style", "stop-color: {hex} {color};stop-opacity:1;".format(
                    hex=hexcode, color=iccColor))
            swatchMain.appendChild(swatchSub)
            svgDefs.appendChild(swatchMain)
            svgSingleSwatch = svgDoc.createElement("rect")
            svgSingleSwatch.setAttribute("x", str(int(Column * 20)))
            svgSingleSwatch.setAttribute("y", str(int(Row * 20)))
            svgSingleSwatch.setAttribute("width", str(int(20)))
            svgSingleSwatch.setAttribute("height", str(int(20)))
            svgSingleSwatch.setAttribute("fill", "url(#%s)" % swatchName)
            svgSingleSwatch.setAttribute("id", "swatch %s" % swatchName)
            if entry.spotColor() is True:
                svgSingleSwatch.setAttribute("rx", str(10))
                svgSingleSwatch.setAttribute("ry", str(10))
            svgSwatches.appendChild(svgSingleSwatch)
            Column += 1
            if (Column >= self.currentPalette.columnCount()):
                Column = 0
                Row += 1

        groupNames = self.currentPalette.groupNames()
        for groupName in groupNames:
            Column = 0
            Row += 1
            groupTitle = svgDoc.createElement("text")
            groupTitle.setAttribute("x", str(int(Column * 20)))
            groupTitle.setAttribute("y", str(int(Row * 20) + 15))
            groupTitle.appendChild(svgDoc.createTextNode(groupName))
            svgSwatches.appendChild(groupTitle)
            Row += 1
            colorCount = self.currentPalette.colorsCountGroup(groupName)
            for i in range(colorCount):
                entry = self.currentPalette.colorSetEntryFromGroup(
                    i, groupName)
                color = self.currentPalette.colorForEntry(entry)
                iccColor = "icc-color(" + color.colorProfile()
                for c in range(len(color.componentsOrdered()) - 1):
                    iccColor = "{col},{c}".format(
                        col=iccColor, c=color.componentsOrdered()[c])
                iccColor = iccColor + ")"
                if color.colorProfile() not in iccProfileList:
                    iccProfileList.append(color.colorProfile())
                # convert to sRGB
                color.setColorSpace("RGBA", "U8", "sRGB built-in")
                red = max(min(int(color.componentsOrdered()[0] * 255), 255), 0)
                green = max(min(int(color.componentsOrdered()[1] * 255), 255),
                            0)
                blue = max(min(int(color.componentsOrdered()[2] * 255), 255),
                           0)
                hexcode = "#{red:02x}{green:02x}{blue:02x}".format(red=red,
                                                                   green=green,
                                                                   blue=blue)
                swatchName = groupName + str(i) + "-" + entry.name()
                swatchName = swatchName.replace(" ", "-")
                swatchName = swatchName.replace("(", "-")
                swatchName = swatchName.replace(")", "-")
                swatchMain = svgDoc.createElement("linearGradient")
                swatchMain.setAttribute("osb:paint", "solid")
                swatchMain.setAttribute("id", swatchName)
                swatchSub = svgDoc.createElement("stop")
                swatchSub.setAttribute(
                    "style",
                    "stop-color: {hex} {color};stop-opacity:1;".format(
                        hex=hexcode, color=iccColor))

                swatchMain.appendChild(swatchSub)
                svgDefs.appendChild(swatchMain)
                svgSingleSwatch = svgDoc.createElement("rect")
                svgSingleSwatch.setAttribute("x", str(int(Column * 20)))
                svgSingleSwatch.setAttribute("y", str(int(Row * 20)))
                svgSingleSwatch.setAttribute("width", str(int(20)))
                svgSingleSwatch.setAttribute("height", str(int(20)))
                svgSingleSwatch.setAttribute("fill", "url(#%s)" % swatchName)
                svgSingleSwatch.setAttribute("id", "swatch %s" % swatchName)
                if entry.spotColor() is True:
                    svgSingleSwatch.setAttribute("rx", str(10))
                    svgSingleSwatch.setAttribute("ry", str(10))
                svgSwatches.appendChild(svgSingleSwatch)
                Column += 1
                if (Column >= self.currentPalette.columnCount()):
                    Column = 0
                    Row += 1

        for profile in iccProfileList:
            svgProfileDesc = svgDoc.createElement("color-profile")
            svgProfileDesc.setAttribute("name", profile)
            # This is incomplete because python api doesn't have any
            # way to ask for this data yet.
            # svgProfileDesc.setAttribute("local", "sRGB")
            # svgProfileDesc.setAttribute("xlink:href", colorprofileurl)
            svgProfileDesc.setAttribute("rendering-intent", "perceptual")
            svgDefs.appendChild(svgProfileDesc)
        svgBaseElement.appendChild(svgDefs)
        svgBaseElement.appendChild(svgSwatches)
        svgBaseElement.setAttribute(
            "viewBox", "0 0 {cols} {row}".format(
                cols=self.currentPalette.columnCount() * 20,
                row=int((Row + 1) * 20)))
        svgDoc.appendChild(svgBaseElement)
        svgFile.write(svgDoc.toString())
        svgFile.close()
Exemple #4
0
class PaletteDocker(DockWidget):
    # Init the docker

    def __init__(self):
        super(PaletteDocker, self).__init__()
        # make base-widget and layout
        widget = QWidget()
        layout = QVBoxLayout()
        buttonLayout = QHBoxLayout()
        widget.setLayout(layout)
        self.setWindowTitle(i18n("Python Palette Docker"))

        # Make a combobox and add palettes
        self.cmb_palettes = QComboBox()
        allPalettes = Application.resources("palette")
        for palette_name in allPalettes:
            self.cmb_palettes.addItem(palette_name)
            self.cmb_palettes.model().sort(0)

        if len(allPalettes.keys()) > 0:
            self.currentPalette = Palette(list(allPalettes.values())[0])
        else:
            self.currentPalette = None

        self.cmb_palettes.currentTextChanged.connect(self.slot_paletteChanged)
        layout.addWidget(self.cmb_palettes)  # add combobox to the layout
        self.paletteView = PaletteView()
        self.paletteView.setPalette(self.currentPalette)
        layout.addWidget(self.paletteView)
        self.paletteView.entrySelectedForeGround.connect(
            self.slot_swatchSelected)

        self.colorComboBox = QComboBox()
        self.colorList = list()
        buttonLayout.addWidget(self.colorComboBox)
        self.bnSetColor = QToolButton()
        self.bnSetColor.setText(i18n("Set"))
        self.bnSetColor.clicked.connect(self.slot_get_color_from_combobox)
        buttonLayout.addWidget(self.bnSetColor)

        self.addEntry = QAction(self)
        self.addEntry.setIconText(i18n("+"))
        self.addEntry.triggered.connect(self.slot_add_entry)
        self.addGroup = QAction(self)
        self.addGroup.triggered.connect(self.slot_add_group)
        self.addGroup.setText(i18n("Add Group"))
        self.addGroup.setIconText(str("\U0001F4C2"))
        self.removeEntry = QAction(self)
        self.removeEntry.setText(i18n("Remove Entry"))
        self.removeEntry.setIconText("-")
        self.removeEntry.triggered.connect(self.slot_remove_entry)
        addEntryButton = QToolButton()
        addEntryButton.setDefaultAction(self.addEntry)
        buttonLayout.addWidget(addEntryButton)
        addGroupButton = QToolButton()
        addGroupButton.setDefaultAction(self.addGroup)
        buttonLayout.addWidget(addGroupButton)
        removeEntryButton = QToolButton()
        removeEntryButton.setDefaultAction(self.removeEntry)
        buttonLayout.addWidget(removeEntryButton)

        # QActions
        self.extra = QToolButton()
        self.editPaletteData = QAction(self)
        self.editPaletteData.setText(i18n("Edit Palette Settings"))
        self.editPaletteData.triggered.connect(self.slot_edit_palette_data)
        self.extra.setDefaultAction(self.editPaletteData)
        buttonLayout.addWidget(self.extra)
        self.actionMenu = QMenu()
        self.exportToGimp = QAction(self)
        self.exportToGimp.setText(i18n("Export as GIMP Palette File"))
        self.exportToGimp.triggered.connect(self.slot_export_to_gimp_palette)
        self.exportToInkscape = QAction(self)
        self.exportToInkscape.setText(
            i18n("Export as Inkscape SVG with Swatches"))
        self.exportToInkscape.triggered.connect(
            self.slot_export_to_inkscape_svg)
        self.sortColors = QAction(self)
        self.sortColors.setText(i18n("Sort Colors"))
        self.sortColors.triggered.connect(self.slot_sort_colors)
        self.actionMenu.addAction(self.editPaletteData)
        self.actionMenu.addAction(self.exportToGimp)
        self.actionMenu.addAction(self.exportToInkscape)
        # self.actionMenu.addAction(self.sortColors)

        self.extra.setMenu(self.actionMenu)

        layout.addLayout(buttonLayout)
        self.slot_fill_combobox()
        self.setWidget(widget)  # add widget to the docker

    def slot_paletteChanged(self, name):
        allPalettes = Application.resources("palette")
        if len(allPalettes) > 0 and name in allPalettes:
            self.currentPalette = Palette(
                Application.resources("palette")[name])
            self.paletteView.setPalette(self.currentPalette)
            self.slot_fill_combobox()

    @pyqtSlot('KisSwatch')
    def slot_swatchSelected(self, entry):
        if (self.canvas()) is not None:
            if (self.canvas().view()) is not None:
                name = entry.name()
                if len(entry.id) > 0:
                    name = entry.id() + " - " + entry.name()
                if len(name) > 0:
                    if name in self.colorList:
                        self.colorComboBox.setCurrentIndex(
                            self.colorList.index(name))
                color = self.currentPalette.colorForEntry(entry)
                self.canvas().view().setForeGroundColor(color)

    def slot_fill_combobox(self):
        '''A function for making a combobox with the available colors. We use
        QCompleter on the colorComboBox so that people can type in the
        name of a color to select it. This is useful for people with
        carefully made palettes where the colors are named properly,
        which makes it easier for them to find colors.
        '''

        if self.currentPalette is None:
            pass
        self.colorComboBox.clear()
        self.colorList = list()
        #        palette = self.currentPalette
        #        for info in palette.infoList():
        #            entry = info.swatch
        #            color = palette.colorForEntry(entry).colorForCanvas(self.canvas())
        #            colorSquare = QPixmap(12, 12)
        #            if entry.spotColor() is True:
        #                img = colorSquare.toImage()
        #                circlePainter = QPainter()
        #                img.fill(self.colorComboBox.palette().color(QPalette.Base))
        #                circlePainter.begin(img)
        #                brush = QBrush(Qt.SolidPattern)
        #                brush.setColor(color)
        #                circlePainter.setBrush(brush)
        #                circlePainter.pen().setWidth(0)
        #                circlePainter.drawEllipse(0, 0, 11, 11)
        #                circlePainter.end()
        #                colorSquare = QPixmap.fromImage(img)
        #            else:
        #                colorSquare.fill(color)
        #            name = entry.name()
        #            if len(entry.id()) > 0:
        #                name = entry.id() + " - " + entry.name()
        #            self.colorList.append(name)
        #            self.colorComboBox.addItem(QIcon(colorSquare), name)
        self.colorComboBox.setEditable(True)
        self.colorComboBox.setInsertPolicy(QComboBox.NoInsert)
        self.colorComboBox.completer().setCompletionMode(
            QCompleter.PopupCompletion)
        self.colorComboBox.completer().setCaseSensitivity(False)
        self.colorComboBox.completer().setFilterMode(Qt.MatchContains)

    def slot_get_color_from_combobox(self):
        if self.currentPalette is not None:
            entry = self.currentPalette.colorSetEntryByIndex(
                self.colorComboBox.currentIndex())
            self.slot_swatchSelected(entry)

    def slot_add_entry(self):
        if (self.canvas()) is not None:
            if (self.canvas().view()) is not None:
                color = self.canvas().view().foregroundColor()
                success = self.paletteView.addEntryWithDialog(color)
                if success is True:
                    self.slot_fill_combobox()

    def slot_add_group(self):
        success = self.paletteView.addGroupWithDialog()
        if success is True:
            self.slot_fill_combobox()

    def slot_remove_entry(self):
        success = self.paletteView.removeSelectedEntryWithDialog()
        if success is True:
            self.slot_fill_combobox()

    def slot_edit_palette_data(self):
        '''A function for giving a gui to edit palette metadata... I also
        want this to be the way to edit the settings of the palette
        docker.
        '''

        dialog = QDialog(self)
        tabWidget = QTabWidget()
        dialog.setWindowTitle(i18n("Edit Palette Data"))
        dialog.setLayout(QVBoxLayout())
        dialog.layout().addWidget(tabWidget)
        paletteWidget = QWidget()
        paletteWidget.setLayout(QVBoxLayout())
        tabWidget.addTab(paletteWidget, i18n("Palette Data"))
        paletteName = QLineEdit()
        paletteName.setText(self.cmb_palettes.currentText())
        paletteWidget.layout().addWidget(paletteName)
        paletteColumns = QSpinBox()
        paletteColumns.setValue(self.currentPalette.columnCount())
        paletteWidget.layout().addWidget(paletteColumns)
        paletteComment = QPlainTextEdit()
        paletteComment.appendPlainText(self.currentPalette.comment())
        paletteWidget.layout().addWidget(paletteComment)
        buttons = QDialogButtonBox(QDialogButtonBox.Ok)
        dialog.layout().addWidget(buttons)
        buttons.accepted.connect(dialog.accept)
        # buttons.rejected.connect(dialog.reject())

        if dialog.exec_() == QDialog.Accepted:
            Resource = Application.resources("palette")[
                self.cmb_palettes.currentText()]
            Resource.setName(paletteName.text())
            self.currentPalette = Palette(Resource)
            self.currentPalette.setColumnCount(paletteColumns.value())
            self.paletteView.setPalette(self.currentPalette)
            self.slot_fill_combobox()
            self.currentPalette.setComment(paletteComment.toPlainText())
            self.currentPalette.save()

    def slot_export_to_gimp_palette(self):
        palette_exporter_gimppalette.gimpPaletteExporter(
            self.cmb_palettes.currentText())

    def slot_export_to_inkscape_svg(self):
        palette_exporter_inkscapeSVG.inkscapeSVGExporter(
            self.cmb_palettes.currentText())

    def slot_sort_colors(self):
        colorSorter = palette_sortColors.sortColors(
            self.cmb_palettes.currentText())
        self.paletteView.setPalette(colorSorter.palette())

    def canvasChanged(self, canvas):
        self.cmb_palettes.clear()
        allPalettes = Application.resources("palette")
        for palette_name in allPalettes:
            self.cmb_palettes.addItem(palette_name)
            self.cmb_palettes.model().sort(0)

        if self.currentPalette is None and len(allPalettes.keys()) > 0:
            self.currentPalette = Palette(list(allPalettes.values())[0])