void VerticalSymmetry::generateStrokes(const Stroke& mainStroke, Strokes& strokes, ToolLoop* loop) { int adjust = (loop->getBrush()->bounds().h % 2); strokes.push_back(mainStroke); Stroke stroke2; for (const auto& pt : mainStroke) stroke2.addPoint(gfx::Point(pt.x, m_y - (pt.y - m_y + adjust))); strokes.push_back(stroke2); }
void HorizontalSymmetry::generateStrokes(const Stroke& mainStroke, Strokes& strokes, ToolLoop* loop) { int adjust = (loop->getBrush()->bounds().w % 2); strokes.push_back(mainStroke); Stroke stroke2; for (const auto& pt : mainStroke) stroke2.addPoint(gfx::Point(m_x - (pt.x - m_x + adjust), pt.y)); strokes.push_back(stroke2); }
Strokes::Strokes(Strokes &strks) { strokes.clear(); for (Stroke *stroke = strks.first(); (stroke = strks.current()); strks.next()) { QString d = stroke->serialize(); addStroke(stroke->serialize()); } maxX = strks.getMaxX(); maxY = strks.getMaxY(); currentStroke = 0; }
static bool parseDeviceScribblePage(const sketch::PageKey &key, const sketch::SketchPagePtr &page, PageScribble &parsedScribble) { bool ok = false; int num_page = key.toInt(&ok); if (!ok) { std::cerr<<"["<<__FILE__<<", "<<__func__<<", "<<__LINE__<<"]"<<"parse PageKey to decimal failed: "<<key.toStdString()<<std::endl; assert(false); return false; } parsedScribble.page_ = num_page; Strokes strokes = page.get()->strokes(); std::cout<<strokes.size()<<" strokes in page"<<std::endl; int i = 0; for (StrokesIter it = strokes.begin(); it != strokes.end(); it++) { std::cout<<"parsing stroke "<<i<<std::endl; i++; const ZoomFactor stroke_zoom_factor = it->get()->zoom(); std::vector<PAPoint> pa_points; Points points = (*it).get()->points(); std::cout<<points.size()<<" points in stroke"<<std::endl; int j = 0; for (PointsIter pit = points.begin(); pit != points.end(); pit++) { j++; pa_points.push_back(PAPoint(pit->x() / stroke_zoom_factor, pit->y() / stroke_zoom_factor)); } if (pa_points.size() == 0) { std::cerr<<"["<<__FILE__<<", "<<__func__<<", "<<__LINE__<<"]"<<"0 points in SketchStroke"<<std::endl; assert(false); continue; } const double stroke_thickness = sketch::getPenSize(it->get()->shape()) / stroke_zoom_factor; const int GRAY_MAX = 0xFF; const double stroke_gray = sketch::getPenColor(it->get()->color()) / static_cast<double>(GRAY_MAX); parsedScribble.strokes_.push_back(PageScribble::Stroke(pa_points, stroke_thickness, stroke_gray)); } return true; }
bool NotesFileParser::startElement(const QString &, const QString &, const QString &qName, const QXmlAttributes &attr) { if (qName == "config") { inConfig = true; } else if (qName == "backup" && inConfig) { emit backupLoaded(attr.value("save") == "yes" ? true : false, attr.value("location")); } else if (qName == "notes" && inConfig) { emit notesShowReminderAtStartUpLoaded(attr.value("showreminder") == "no" ? false : true); } else if (qName == "security" && inConfig) { emit securityPasswdLoaded(attr.value("passwd")); } else if (qName == "entry") { entryName = attr.value("name"); entry = new Entry(entryName); entry->setDefaultPic(attr.value("defaultpic")); } else if (qName == "property" && entry) { PropertyStruct *ps = new PropertyStruct(attr.value("name"), attr.value("type") == "oneLine" ? PropertyStruct::ONE_LINE : PropertyStruct::MULTI_LINE); entry->addProperty(ps); } else if (qName == "note") { QList<QString> *data = new QList<QString>; Strokes *strokes = new Strokes; QString en, n, per, day, month, year, hour, min, pic = "", rday, rmonth, ryear, rhour, rmin; int startIdx = 2, prio = 0; QDateTime dt, rem; n = attr.value("name"); per = attr.value("percentage"); // It's task if (per.length()) { prio = attr.value("priority").toInt(); startIdx += 2; } day = attr.value("day"); // It's event if (day.length()) { month = attr.value("month"); year = attr.value("year"); startIdx += 3; dt.setDate(QDate(year.toInt(), month.toInt(), day.toInt())); hour = attr.value("hour"); if (hour.length()) { min = attr.value("min"); startIdx += 2; dt.setTime(QTime(hour.toInt(), min.toInt())); } else dt.setTime(QTime(25, 61)); } rday = attr.value("rday"); // has reminder if (rday.length()) { rmonth = attr.value("rmonth"); ryear = attr.value("ryear"); startIdx += 3; rem.setDate(QDate(ryear.toInt(), rmonth.toInt(), rday.toInt())); rhour = attr.value("rhour"); if (rhour.length()) { rmin = attr.value("rmin"); startIdx += 2; rem.setTime(QTime(rhour.toInt(), rmin.toInt())); } else rem.setTime(QTime(25, 61)); } // Has pic pic = attr.value("pic"); if (pic.length()) { startIdx += 1; } // Text note if ((en = attr.value("type")) == "Text") { delete strokes; en = ""; data->append(new QString(attr.value("data0"))); emit noteLoaded(n, data, en, per, prio, dt, pic, rem); } // Sketch note else if (en == "Sketch") { delete data; for (int i = startIdx; i < attr.length(); i++) { strokes->addStroke(attr.value(i)); } emit noteLoaded(n, strokes, en, per, prio, dt, pic, rem); } // Defined note else { delete strokes; for (int i = startIdx; i < attr.length(); i++) { data->append(new QString(attr.value(i))); } emit noteLoaded(n, data, en, per, prio, dt, pic, rem); } } return true; }
void ToolLoopManager::doLoopStep(bool last_step) { // Original set of points to interwine (original user stroke, // relative to sprite origin). Stroke main_stroke; if (!last_step) m_toolLoop->getController()->getStrokeToInterwine(m_stroke, main_stroke); else main_stroke = m_stroke; // Calculate the area to be updated in all document observers. Symmetry* symmetry = m_toolLoop->getSymmetry(); Strokes strokes; if (symmetry) symmetry->generateStrokes(main_stroke, strokes, m_toolLoop); else strokes.push_back(main_stroke); calculateDirtyArea(strokes); // Validate source image area. if (m_toolLoop->getInk()->needsSpecialSourceArea()) { gfx::Region srcArea; m_toolLoop->getInk()->createSpecialSourceArea(m_dirtyArea, srcArea); m_toolLoop->validateSrcImage(srcArea); } else { m_toolLoop->validateSrcImage(m_dirtyArea); } m_toolLoop->getInk()->prepareForStrokes(m_toolLoop, strokes); // Invalidate destionation image areas. if (m_toolLoop->getTracePolicy() == TracePolicy::Last) { // Copy source to destination (reset the previous trace). Useful // for tools like Line and Ellipse (we kept the last trace only). m_toolLoop->invalidateDstImage(); } else if (m_toolLoop->getTracePolicy() == TracePolicy::AccumulateUpdateLast) { // Revalidate only this last dirty area (e.g. pixel-perfect // freehand algorithm needs this trace policy to redraw only the // last dirty area, which can vary in one pixel from the previous // tool loop cycle). m_toolLoop->invalidateDstImage(m_dirtyArea); } m_toolLoop->validateDstImage(m_dirtyArea); // Join or fill user points if (!m_toolLoop->getFilled() || (!last_step && !m_toolLoop->getPreviewFilled())) m_toolLoop->getIntertwine()->joinStroke(m_toolLoop, main_stroke); else m_toolLoop->getIntertwine()->fillStroke(m_toolLoop, main_stroke); if (m_toolLoop->getTracePolicy() == TracePolicy::Overlap) { // Copy destination to source (yes, destination to source). In // this way each new trace overlaps the previous one. m_toolLoop->copyValidDstToSrcImage(m_dirtyArea); } if (!m_dirtyArea.isEmpty()) m_toolLoop->updateDirtyArea(); }