Ejemplo n.º 1
0
    def __draw_link(self, name: str, points: Sequence[int]) -> None:
        """Draw link function.

        The link color will be the default color.
        """
        pen = QPen(Qt.black if self.monochrome else color_qt('blue'))
        pen.setWidth(self.link_width)
        self.painter.setPen(pen)
        brush = color_qt('dark-gray') if self.monochrome else LINK_COLOR
        brush.setAlphaF(0.70)
        self.painter.setBrush(brush)
        qpoints = tuple(
            QPointF(self.pos[i][0], -self.pos[i][1]) * self.zoom
            for i in points if self.pos[i] and (not isnan(self.pos[i][0]))
        )
        if len(qpoints) == len(points):
            self.painter.drawPolygon(*qpoints)
        self.painter.setBrush(Qt.NoBrush)
        if self.show_point_mark and name != VLink.FRAME and qpoints:
            pen.setColor(Qt.darkGray)
            self.painter.setPen(pen)
            self.painter.setFont(QFont('Arial', self.font_size))
            cen_x = sum(self.pos[i][0] for i in points if self.pos[i])
            cen_y = sum(self.pos[i][1] for i in points if self.pos[i])
            self.painter.drawText(
                QPointF(cen_x, -cen_y) * self.zoom / len(points),
                f"[{name}]"
            )
Ejemplo n.º 2
0
 def __draw_path(self) -> None:
     """Draw paths. Recording first."""
     paths = self.path_record or self.path.path or self.path_preview
     if len(self.vpoints) != len(paths):
         return
     pen = QPen()
     fmt_paths: List[Tuple[int, _Path]] = list(enumerate(paths))
     if paths is self.path_preview:
         fmt_paths.extend(self.slider_path_preview.items())
     for i, path in fmt_paths:
         if self.path.show != i and self.path.show != -1:
             continue
         if self.monochrome:
             color = color_qt('gray')
         elif self.vpoints[i].color is None:
             color = color_qt('green')
         else:
             color = QColor(*self.vpoints[i].color)
         pen.setColor(color)
         pen.setWidth(self.path_width)
         self.painter.setPen(pen)
         if self.path.curve:
             self.draw_curve(path)
         else:
             self.draw_dot(path)
 def __draw_path(self) -> None:
     """Draw paths. Recording first."""
     paths: _Paths = self.path_record or self.path.path or self.path_preview
     if len(self.vpoints) != len(paths):
         return
     pen = QPen()
     fmt_paths = [(i, p) for i, p in enumerate(paths)]
     if paths is self.path_preview:
         fmt_paths.extend(self.slider_path_preview.items())
     elif paths is self.path_record:
         fmt_paths.extend(self.slider_record.items())
     else:
         # User paths
         fmt_paths.extend(self.path.slider_path.items())
     for i, path in fmt_paths:
         if self.path.show != i and self.path.show != -1:
             continue
         vpoint = self.vpoints[i]
         if self.monochrome:
             color = color_qt('gray')
         else:
             color = color_qt(vpoint.color)
         pen.setColor(color)
         pen.setWidth(self.path_width)
         self.painter.setPen(pen)
         if self.path.curve:
             self.draw_curve(path)
         else:
             self.draw_dot(path)
Ejemplo n.º 4
0
 def paintEvent(self, event: QPaintEvent) -> None:
     """Drawing function."""
     super(_DynamicCanvas, self).paintEvent(event)
     pen = QPen()
     pen.setWidth(self.link_width)
     brush = color_qt('dark-gray') if self.monochrome else LINK_COLOR
     self.painter.setBrush(brush)
     for vlink in self.vlinks:
         if vlink.name == VLink.FRAME or not vlink.points:
             continue
         points = []
         for i in vlink.points:
             vpoint = self.vpoints[i]
             if (vpoint.type == VJoint.R
                     or not vpoint.is_slot_link(vlink.name)):
                 x, y = self.path.path[i][self.ind]
             else:
                 x, y = self.path.slider_path[i][self.ind]
             points.append((x * self.zoom, y * -self.zoom))
         qpoints = convex_hull(points, as_qpoint=True)
         pen.setColor(
             Qt.black if self.monochrome else color_qt(vlink.color))
         self.painter.setPen(pen)
         self.painter.drawPolygon(*qpoints)
     self.painter.setBrush(Qt.NoBrush)
     pen.setWidth(self.path_width)
     for paths, vel, acc in [
         (enumerate(self.path.path), self.vel, self.acc),
         (self.path.slider_path.items(), self.vel_slider, self.acc_slider),
     ]:
         for i, path in paths:
             vpoint = self.vpoints[i]
             if self.monochrome:
                 color = color_qt('gray')
             else:
                 color = color_qt(vpoint.color)
             pen.setColor(color)
             self.painter.setPen(pen)
             self.draw_curve(path)
             x, y = path[self.ind]
             zoom = 1.
             for vec, color in [(vel[i], Qt.blue), (acc[i], Qt.red)]:
                 if self.ind >= len(vec):
                     break
                 vx, vy = vec[self.ind]
                 if isnan(vx) or isnan(vy):
                     break
                 zoom /= self.factor
                 r = hypot(vx, vy) * zoom
                 if isclose(r, 0):
                     break
                 th = atan2(vy, vx)
                 pen.setColor(color)
                 self.painter.setPen(pen)
                 self.draw_arrow(x, y, x + r * cos(th), y + r * sin(th))
             self.draw_point(i, x, y, vpoint.grounded(), vpoint.color)
     self.painter.end()
Ejemplo n.º 5
0
 def __draw_paths(self) -> None:
     """Draw paths."""
     pen = QPen()
     pen.setWidth(self.path_width)
     for i, path in enumerate(self.path.path):
         if self.monochrome:
             pen.setColor(color_qt('gray'))
         elif self.vpoints[i].color is None:
             pen.setColor(color_qt('green'))
         else:
             pen.setColor(QColor(*self.vpoints[i].color))
         self.painter.setPen(pen)
         self.draw_curve(path)
Ejemplo n.º 6
0
    def __draw_path(self) -> None:
        """Draw a path.

        A simple function than main canvas.
        """
        pen = QPen()
        for i, path in enumerate(self.path.path):
            color = color_qt('Green')
            if f"P{i}" in self.target_path:
                color = color_qt('Dark-Orange')
            pen.setColor(color)
            pen.setWidth(self.path_width)
            self.painter.setPen(pen)
            self.draw_curve(path)
 def __draw_link(self, vlink: VLink) -> None:
     """Draw a link."""
     if vlink.name == VLink.FRAME or not vlink.points:
         return
     pen = QPen()
     # Rearrange: Put the nearest point to the next position.
     qpoints = convex_hull(
         [(c.x * self.zoom, c.y * -self.zoom)
          for c in vlink.points_pos(self.vpoints)], as_qpoint=True)
     if (
         self.select_mode == SelectMode.LINK
         and self.vlinks.index(vlink) in self.selections
     ):
         pen.setWidth(self.link_width + 6)
         pen.setColor(Qt.black if self.monochrome else QColor(161, 16, 239))
         self.painter.setPen(pen)
         self.painter.drawPolygon(*qpoints)
     pen.setWidth(self.link_width)
     pen.setColor(Qt.black if self.monochrome else color_qt(vlink.color))
     self.painter.setPen(pen)
     self.painter.drawPolygon(*qpoints)
     if not self.show_point_mark:
         return
     pen.setColor(Qt.darkGray)
     self.painter.setPen(pen)
     p_count = len(qpoints)
     cen_x = sum(p.x() for p in qpoints) / p_count
     cen_y = sum(p.y() for p in qpoints) / p_count
     self.painter.drawText(
         QRectF(cen_x - 50, cen_y - 50, 100, 100),
         Qt.AlignCenter,
         f'[{vlink.name}]'
     )
Ejemplo n.º 8
0
 def __draw_link(self, vlink: VLink) -> None:
     """Draw a link."""
     if vlink.name == VLink.FRAME or not vlink.points:
         return
     points = self.__points_pos(vlink)
     pen = QPen()
     # Rearrange: Put the nearest point to the next position.
     qpoints = convex_hull(points, as_qpoint=True)
     if (self.select_mode == SelectMode.LINK
             and self.vlinks.index(vlink) in self.selections):
         pen.setWidth(self.link_width + 6)
         pen.setColor(Qt.black if self.monochrome else QColor(161, 16, 239))
         self.painter.setPen(pen)
         self.painter.drawPolygon(*qpoints)
     pen.setWidth(self.link_width)
     pen.setColor(Qt.black if self.monochrome else QColor(*vlink.color))
     self.painter.setPen(pen)
     brush = color_qt('dark-gray') if self.monochrome else LINK_COLOR
     brush.setAlphaF(self.transparency)
     self.painter.setBrush(brush)
     self.painter.drawPolygon(*qpoints)
     self.painter.setBrush(Qt.NoBrush)
     if not self.show_point_mark:
         return
     pen.setColor(Qt.darkGray)
     self.painter.setPen(pen)
     p_count = len(points)
     cen_x = sum(p[0] for p in points) / p_count
     cen_y = sum(p[1] for p in points) / p_count
     self.painter.drawText(QRectF(cen_x - 50, cen_y - 50, 100, 100),
                           Qt.AlignCenter, f'[{vlink.name}]')
Ejemplo n.º 9
0
 def __set_rgb(self) -> None:
     """Add a custom color from current color."""
     color = QColorDialog.getColor(
         color_qt(self.color_box.currentText()),
         self
     )
     if color.isValid():
         add_custom_color(self.color_box, color)
Ejemplo n.º 10
0
    def __draw_path(self) -> None:
        """Draw a path.

        A simple function than main canvas.
        """
        pen = QPen()
        pen.setWidth(self.path_width)
        for i, path in enumerate(self.path.path):
            if self.no_mechanism and i not in self.target_path:
                continue
            if i in self.target_path:
                if self.monochrome:
                    color = color_qt('black')
                else:
                    color = color_qt('dark-orange')
            else:
                if self.monochrome:
                    color = color_qt('gray')
                else:
                    color = color_qt('green')
            pen.setColor(color)
            self.painter.setPen(pen)
            self.draw_curve(path)
Ejemplo n.º 11
0
 def paintEvent(self, event: QPaintEvent) -> None:
     """Drawing functions."""
     width = self.width()
     height = self.height()
     if self.width_old is None:
         self.width_old = width
     if self.height_old is None:
         self.height_old = height
     if self.width_old != width or self.height_old != height:
         self.ox += (width - self.width_old) / 2
         self.oy += (height - self.height_old) / 2
     # 'self' is the instance of 'DynamicCanvas'.
     BaseCanvas.paintEvent(self, event)
     # Draw links except ground
     brush = color_qt('dark-gray') if self.monochrome else LINK_COLOR
     brush.setAlphaF(self.transparency)
     self.painter.setBrush(brush)
     for vlink in self.vlinks[1:]:
         self.__draw_link(vlink)
     self.painter.setBrush(Qt.NoBrush)
     # Draw path
     if self.path.show != -2:
         self.__draw_path()
     # Draw solving path
     if self.show_target_path:
         self.painter.setFont(QFont("Arial", self.font_size + 5))
         self.draw_ranges()
         self.draw_target_path()
         self.painter.setFont(QFont("Arial", self.font_size))
     # Draw points
     for i, vpoint in enumerate(self.vpoints):
         self.__draw_point(i, vpoint)
     # Draw solutions
     if self.select_mode == SelectMode.SOLUTION:
         for i, expr in enumerate(self.exprs):
             func = expr[0]
             params = expr[1:-1]
             target = expr[-1]
             self.draw_solution(func, params, target, self.vpoints)
             if i in self.selections:
                 pos, _ = self.solution_polygon(func, params, target,
                                                self.vpoints)
                 pen = QPen()
                 pen.setWidth(self.link_width + 3)
                 pen.setColor(QColor(161, 16, 239))
                 self.painter.setPen(pen)
                 self.painter.drawPolygon(QPolygonF([QPointF(x, y)
                                                     for x, y in pos]))
     # Draw a colored frame for free move mode
     if self.free_move != FreeMode.NO_FREE_MOVE:
         pen = QPen()
         if self.free_move == FreeMode.TRANSLATE:
             pen.setColor(QColor(161, 16, 229))
         elif self.free_move == FreeMode.ROTATE:
             pen.setColor(QColor(219, 162, 6))
         elif self.free_move == FreeMode.REFLECT:
             pen.setColor(QColor(79, 249, 193))
         pen.setWidth(8)
         self.painter.setPen(pen)
         self.__draw_frame()
     # Rectangular selection
     if self.selector.picking:
         pen = QPen(Qt.gray)
         pen.setWidth(1)
         self.painter.setPen(pen)
         self.painter.drawRect(self.selector.to_rect(self.zoom))
     # Show FPS
     self.fps_updated.emit()
     self.painter.end()
     # Record the widget size
     self.width_old = width
     self.height_old = height
Ejemplo n.º 12
0
    def __draw_point(self, i: int, vpoint: VPoint) -> None:
        """Draw a point."""
        connected = len(vpoint.links) - 1
        if vpoint.type in {VJoint.P, VJoint.RP}:
            pen = QPen(color_qt(vpoint.color))
            pen.setWidth(2)
            # Draw slot point and pin point
            for j, (cx, cy) in enumerate(vpoint.c):
                # Slot point
                if j == 0 or vpoint.type == VJoint.P:
                    if self.monochrome:
                        color = Qt.black
                    else:
                        color = color_qt(vpoint.color)
                    pen.setColor(color)
                    self.painter.setPen(pen)
                    cp = QPointF(cx, -cy) * self.zoom
                    jr = self.joint_size * (2 if j == 0 else 1)
                    rp = QPointF(jr, -jr)
                    self.painter.drawRect(QRectF(cp + rp, cp - rp))
                    if self.show_point_mark:
                        pen.setColor(Qt.darkGray)
                        self.painter.setPen(pen)
                        text = f"[Point{i}]"
                        if self.show_dimension:
                            text += f":({cx:.02f}, {cy:.02f})"
                        self.painter.drawText(cp + rp, text)
                else:
                    grounded = (len(vpoint.c) == len(vpoint.links)
                                and vpoint.links[j] == VLink.FRAME)
                    self.draw_point(i, cx, cy, grounded, vpoint.color,
                                    connected)
            # Slider line
            pen.setColor(color_qt(vpoint.color).darker())
            self.painter.setPen(pen)
            qline_m = QLineF(
                QPointF(vpoint.c[1, 0], -vpoint.c[1, 1]) * self.zoom,
                QPointF(vpoint.c[0, 0], -vpoint.c[0, 1]) * self.zoom
            )
            nv = qline_m.normalVector()
            nv.setLength(self.joint_size)
            nv.setPoints(nv.p2(), nv.p1())
            qline_1 = nv.normalVector()
            qline_1.setLength(qline_m.length())
            self.painter.drawLine(qline_1)
            nv.setLength(nv.length() * 2)
            nv.setPoints(nv.p2(), nv.p1())
            qline_2 = nv.normalVector()
            qline_2.setLength(qline_m.length())
            qline_2.setAngle(qline_2.angle() + 180)
            self.painter.drawLine(qline_2)
        else:
            self.draw_point(i, vpoint.cx, vpoint.cy, vpoint.grounded(),
                            vpoint.color, connected)

        # For selects function
        if self.select_mode == SelectMode.JOINT and (i in self.selections):
            pen = QPen(QColor(161, 16, 239))
            pen.setWidth(3)
            self.painter.setPen(pen)
            self.painter.drawRect(
                vpoint.cx * self.zoom - 12,
                vpoint.cy * -self.zoom - 12,
                24, 24
            )