Compare commits
11 Commits
Author | SHA1 | Date | |
---|---|---|---|
78fb3a5458 | |||
02c0e09b5c | |||
cab3dfcb8f | |||
cc3a188275 | |||
7796b8606d | |||
588bd80e8a | |||
065ee35656 | |||
037276bc01 | |||
160a8cc3e8 | |||
e642436651 | |||
4606381495 |
15
README.md
15
README.md
@ -33,11 +33,9 @@ But... I've reinvented one...
|
||||
|
||||
It's the **SENSITIVE** image-labeling tool for object detection!
|
||||
|
||||

|
||||

|
||||
|
||||

|
||||
|
||||

|
||||
https://user-images.githubusercontent.com/35001605/211560039-367f27d7-63ab-4342-824e-9f47f2afbc35.mp4
|
||||
|
||||

|
||||
|
||||
@ -54,7 +52,7 @@ But... I've reinvented one...
|
||||
|
||||
### For Windows
|
||||
|
||||
2. Download [YOLOLabel_20211126_v1.0](https://github.com/developer0hye/Yolo_Label/releases/download/v1.0.0/YoloLabel_v1.0.0.zip)
|
||||
2. Download [YOLOLabel_20211130_v1.1.1](https://github.com/developer0hye/Yolo_Label/releases/download/v1.1.1/YoloLabel_v1.1.1.zip)
|
||||
|
||||
3. Unzip
|
||||
|
||||
@ -94,7 +92,7 @@ yourMacOS:Yolo_Label you$ ./YoloLabel.app/MacOS/YoloLabel
|
||||
|
||||
4. Click the button 'Open Files' and open the folder with the images and the file('*'.names or '*'.txt) with the names of the objects.
|
||||
|
||||

|
||||

|
||||
|
||||
5. And... Label!... Welcome to Hell... I really hate this work in the world.
|
||||
|
||||
@ -128,6 +126,8 @@ To minimize wrist strain when labeling, I adopted the method **"twice left butto
|
||||
| `D, Space` | Save and Next Image |
|
||||
| `S` | Next Label <br>  |
|
||||
| `W` | Prev Label <br>  |
|
||||
| `O` | Open Files |
|
||||
| `V` | Visualize Calss Name |
|
||||
| `Ctrl + S` | Save |
|
||||
| `Ctrl + C` | Delete all existing bounding boxes in the image |
|
||||
| `Ctrl + D` | Delete current image |
|
||||
@ -153,10 +153,13 @@ You can access all image by moving horizontal slider bar. But when you control h
|
||||

|
||||
|
||||
# CONCLUSIONS
|
||||
|
||||
I've reinvented the wheel.
|
||||
|
||||

|
||||
|
||||
# TO DO LISTS
|
||||
|
||||
Upload binary file for easy usage for windows and ubuntu
|
||||
|
||||
deployment for ubuntu
|
||||
|
@ -20,7 +20,7 @@ DEFINES += QT_DEPRECATED_WARNINGS
|
||||
# You can also select to disable deprecated APIs only up to a certain version of Qt.
|
||||
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000 # disables all the APIs deprecated before Qt 6.0.0
|
||||
|
||||
CONFIG += c++11
|
||||
CONFIG += c++1z
|
||||
|
||||
SOURCES += \
|
||||
main.cpp \
|
||||
|
@ -80,6 +80,7 @@ void label_img::init()
|
||||
{
|
||||
m_objBoundingBoxes.clear();
|
||||
m_bLabelingStarted = false;
|
||||
m_bVisualizeClassName = false;
|
||||
m_focusedObjectLabel = 0;
|
||||
|
||||
QPoint mousePosInUi = this->mapFromGlobal(QCursor::pos());
|
||||
@ -125,7 +126,8 @@ void label_img::openImage(const QString &qstrImg, bool &ret)
|
||||
|
||||
m_inputImg = img.copy();
|
||||
m_inputImg = m_inputImg.convertToFormat(QImage::Format_RGB888);
|
||||
m_resized_inputImg = m_inputImg.scaled(this->width(), this->height(),Qt::IgnoreAspectRatio,Qt::SmoothTransformation);
|
||||
m_resized_inputImg = m_inputImg.scaled(this->width(), this->height(),Qt::IgnoreAspectRatio,Qt::SmoothTransformation)
|
||||
.convertToFormat(QImage::Format_RGB888);
|
||||
|
||||
m_bLabelingStarted = false;
|
||||
|
||||
@ -148,7 +150,8 @@ void label_img::showImage()
|
||||
if(m_inputImg.isNull()) return;
|
||||
if(m_resized_inputImg.width() != this->width() or m_resized_inputImg.height() != this->height())
|
||||
{
|
||||
m_resized_inputImg = m_inputImg.scaled(this->width(), this->height(),Qt::IgnoreAspectRatio,Qt::SmoothTransformation);
|
||||
m_resized_inputImg = m_inputImg.scaled(this->width(), this->height(),Qt::IgnoreAspectRatio,Qt::SmoothTransformation)
|
||||
.convertToFormat(QImage::Format_RGB888);
|
||||
}
|
||||
|
||||
QImage img = m_resized_inputImg;
|
||||
@ -156,6 +159,11 @@ void label_img::showImage()
|
||||
gammaTransform(img);
|
||||
|
||||
QPainter painter(&img);
|
||||
QFont font = painter.font();
|
||||
int fontSize = 16, xMargin = 5, yMargin = 2;
|
||||
font.setPixelSize(fontSize);
|
||||
font.setBold(true);
|
||||
painter.setFont(font);
|
||||
|
||||
int penThick = 3;
|
||||
|
||||
@ -164,6 +172,8 @@ void label_img::showImage()
|
||||
drawCrossLine(painter, crossLineColor, penThick);
|
||||
drawFocusedObjectBox(painter, Qt::magenta, penThick);
|
||||
drawObjectBoxes(painter, penThick);
|
||||
if(m_bVisualizeClassName)
|
||||
drawObjectLabels(painter, penThick, fontSize, xMargin, yMargin);
|
||||
|
||||
this->setPixmap(QPixmap::fromImage(img));
|
||||
}
|
||||
@ -279,6 +289,36 @@ void label_img::drawObjectBoxes(QPainter& painter, int thickWidth)
|
||||
}
|
||||
}
|
||||
|
||||
void label_img::drawObjectLabels(QPainter& painter, int thickWidth, int fontPixelSize, int xMargin, int yMargin)
|
||||
{
|
||||
QFontMetrics fontMetrics = painter.fontMetrics();
|
||||
QPen blackPen;
|
||||
|
||||
for(ObjectLabelingBox boundingbox: m_objBoundingBoxes)
|
||||
{
|
||||
QColor labelColor = m_drawObjectBoxColor.at(boundingbox.label);
|
||||
QRect rectUi = cvtRelativeToAbsoluteRectInUi(boundingbox.box);
|
||||
|
||||
QRect labelRect = fontMetrics.boundingRect(m_objList.at(boundingbox.label));
|
||||
if (rectUi.top() > fontPixelSize + yMargin * 2 + thickWidth + 1) {
|
||||
labelRect.moveTo(rectUi.topLeft() + QPoint(-thickWidth / 2, -(fontPixelSize + yMargin * 2 + thickWidth + 1)));
|
||||
labelRect.adjust(0, 0, xMargin * 2, yMargin * 2);
|
||||
} else {
|
||||
labelRect.moveTo(rectUi.topLeft() + QPoint(-thickWidth / 2, 0));
|
||||
labelRect.adjust(0, 0, xMargin * 2, yMargin * 2);
|
||||
}
|
||||
painter.fillRect(labelRect, labelColor);
|
||||
|
||||
if (qGray(m_drawObjectBoxColor.at(boundingbox.label).rgb()) > 120) {
|
||||
blackPen.setColor(QColorConstants::Black);
|
||||
} else {
|
||||
blackPen.setColor(QColorConstants::White);
|
||||
}
|
||||
painter.setPen(blackPen);
|
||||
painter.drawText(labelRect.topLeft() + QPoint(xMargin, yMargin + fontPixelSize), m_objList.at(boundingbox.label));
|
||||
}
|
||||
}
|
||||
|
||||
void label_img::gammaTransform(QImage &image)
|
||||
{
|
||||
uchar* bits = image.bits();
|
||||
|
@ -25,6 +25,7 @@ public:
|
||||
void mouseReleaseEvent(QMouseEvent *ev);
|
||||
|
||||
QVector<QColor> m_drawObjectBoxColor;
|
||||
QStringList m_objList;
|
||||
|
||||
int m_uiX;
|
||||
int m_uiY;
|
||||
@ -33,6 +34,7 @@ public:
|
||||
int m_imgY;
|
||||
|
||||
bool m_bLabelingStarted;
|
||||
bool m_bVisualizeClassName;
|
||||
|
||||
static QColor BOX_COLORS[10];
|
||||
|
||||
@ -86,6 +88,7 @@ private:
|
||||
void drawCrossLine(QPainter& , QColor , int thickWidth = 3);
|
||||
void drawFocusedObjectBox(QPainter& , Qt::GlobalColor , int thickWidth = 3);
|
||||
void drawObjectBoxes(QPainter& , int thickWidth = 3);
|
||||
void drawObjectLabels(QPainter& , int thickWidth = 3, int fontPixelSize = 14, int xMargin = 5, int yMargin = 2);
|
||||
void gammaTransform(QImage& image);
|
||||
void removeFocusedObjectBox(QPointF);
|
||||
};
|
||||
|
@ -8,6 +8,7 @@
|
||||
#include <QShortcut>
|
||||
#include <QCollator>
|
||||
#include <iomanip>
|
||||
#include <cmath>
|
||||
|
||||
using std::cout;
|
||||
using std::endl;
|
||||
@ -249,6 +250,7 @@ void MainWindow::load_label_list_data(QString qstrLabelListFile)
|
||||
|
||||
ui->label_image->m_drawObjectBoxColor.push_back(labelColor);
|
||||
}
|
||||
ui->label_image->m_objList = m_objList;
|
||||
}
|
||||
}
|
||||
|
||||
@ -359,11 +361,6 @@ void MainWindow::open_obj_file(bool& ret)
|
||||
}
|
||||
}
|
||||
|
||||
void MainWindow::reupdate_img_list()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void MainWindow::wheelEvent(QWheelEvent *ev)
|
||||
{
|
||||
if(ev->angleDelta().y() > 0) // up Wheel
|
||||
@ -473,8 +470,14 @@ void MainWindow::init_table_widget()
|
||||
void MainWindow::on_horizontalSlider_contrast_sliderMoved(int value)
|
||||
{
|
||||
float valueToPercentage = float(value)/ui->horizontalSlider_contrast->maximum(); //[0, 1.0]
|
||||
float percentageToGamma = pow(1/(valueToPercentage + 0.5), 7.);
|
||||
float percentageToGamma = std::pow(1/(valueToPercentage + 0.5), 7.);
|
||||
|
||||
ui->label_image->setContrastGamma(percentageToGamma);
|
||||
ui->label_contrast->setText(QString("Contrast(%) ") + QString::number(int(valueToPercentage * 100.)));
|
||||
}
|
||||
|
||||
void MainWindow::on_checkBox_visualize_class_name_clicked(bool checked)
|
||||
{
|
||||
ui->label_image->m_bVisualizeClassName = checked;
|
||||
ui->label_image->showImage();
|
||||
}
|
||||
|
@ -23,10 +23,6 @@ public:
|
||||
|
||||
private slots:
|
||||
void on_pushButton_open_files_clicked();
|
||||
// void on_pushButton_change_dir_clicked();
|
||||
// void on_pushButton_save_clicked();
|
||||
// void on_pushButton_remove_clicked();
|
||||
|
||||
void on_pushButton_prev_clicked();
|
||||
void on_pushButton_next_clicked();
|
||||
|
||||
@ -48,6 +44,8 @@ private slots:
|
||||
|
||||
void on_horizontalSlider_contrast_sliderMoved(int value);
|
||||
|
||||
void on_checkBox_visualize_class_name_clicked(bool checked);
|
||||
|
||||
private:
|
||||
void init();
|
||||
void init_table_widget();
|
||||
@ -71,8 +69,6 @@ private:
|
||||
void open_img_dir(bool&);
|
||||
void open_obj_file(bool&);
|
||||
|
||||
void reupdate_img_list();
|
||||
|
||||
Ui::MainWindow *ui;
|
||||
|
||||
QString m_imgDir;
|
||||
|
@ -57,7 +57,7 @@
|
||||
</size>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout">
|
||||
<item row="0" column="0">
|
||||
<item row="3" column="0">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_5">
|
||||
<item>
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
@ -77,6 +77,7 @@
|
||||
</property>
|
||||
<property name="font">
|
||||
<font>
|
||||
<family>Arial</family>
|
||||
<pointsize>18</pointsize>
|
||||
<weight>75</weight>
|
||||
<bold>true</bold>
|
||||
@ -106,7 +107,7 @@ border-color: rgb(0, 255, 255);}
|
||||
<number>3</number>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string><html><head/><body><p>Open a Dataset Directory...</p><p>D: Next Image</p><p>A: Prev Image</p><p><br/>Ctrl + S: Save</p><p>Ctrl + D: Delete an Image<br/></p></body></html></string>
|
||||
<string><html><head/><body><p>Open a Dataset Directory...</p><p>D: Next Image</p><p>A: Prev Image</p><p>S: Next Class</p><p>W: Prev Class</p><p>V: Visualize Class Name</p><p>O: Open Files<br/>Ctrl + S: Save</p><p>Ctrl + D: Delete an Image<br/></p></body></html></string>
|
||||
</property>
|
||||
<property name="scaledContents">
|
||||
<bool>true</bool>
|
||||
@ -396,6 +397,9 @@ border-color: rgb(0, 255, 255);</string>
|
||||
<property name="text">
|
||||
<string>Open Files</string>
|
||||
</property>
|
||||
<property name="shortcut">
|
||||
<string>O</string>
|
||||
</property>
|
||||
<property name="autoDefault">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
@ -575,6 +579,32 @@ QTableView {
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item row="0" column="0">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_6">
|
||||
<item>
|
||||
<widget class="QCheckBox" name="checkBox_visualize_class_name">
|
||||
<property name="font">
|
||||
<font>
|
||||
<family>Arial</family>
|
||||
<pointsize>12</pointsize>
|
||||
<underline>false</underline>
|
||||
<strikeout>false</strikeout>
|
||||
</font>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">background-color : rgb(0, 0, 17);color : rgb(0, 255, 255);
|
||||
</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Visualize Class Name</string>
|
||||
</property>
|
||||
<property name="shortcut">
|
||||
<string>V</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<widget class="QMenuBar" name="menuBar">
|
||||
|
Reference in New Issue
Block a user