«Это 27-й день моего участия в ноябрьском испытании обновлений. Подробную информацию об этом событии см.:Вызов последнего обновления 2021 г."
предисловие
В этой статье я буду использовать функцию рисования, чтобы узнать, как использовать рисование в реальных проектах для рисования аналоговых часов для отображения текущего времени.
Внешний вид аналоговых часов
комбинироватьOpenCV
построение функций в (например,cv2.line()
,cv2.circle()
иcv2.putText()
и т. д.), чтобы отображать более сложные графики, лучше понимая и фактически применяя известные вам функции построения графиков. Чтобы объединить все функции рисования, создайте аналоговые часы для отображения текущего времени, включая часовую, минутную и секундную стрелки.
Для достижения вышеуказанных требований напишитеclock_appearance.py
сценарий.clock_appearance.py
использование сценарияcv.line()
,cv.circle()
иcv2.putText()
Чтобы нарисовать аналоговые часы, сначала нарисуйте внешний вид статических часов, нам нужны два массива, содержащие фиксированные координаты (о том, как вычисляются эти массивы, будет рассказано в следующем подразделе):
hours_orig = np.array([(620,320), (580, 470), (470, 580), (320, 620), (170, 580), (60, 470), (20, 320), (60, 170), (169, 61), (319, 20), (469, 60), (579, 169)])
hours_dest = np.array([(600,320), (563, 460), (460, 562), (320, 600), (180, 563), (78, 460), (40, 320), (77, 180), (179, 78), (319, 40), (459, 77), (562, 179)])
Эти массивы отображаются小时刻度
Требуется, потому что они определяют почасовые тиковые линии часов. После того, как массив определен, нарисуйте эти галочки:
for i in range(0, 12):
cv2.line(image, array_to_tuple(hours_orig[i]), array_to_tuple(hours_dest[i]), colors['black'], 3)
Также следует нарисовать большой круг, соответствующий форме циферблата аналоговых часов:
cv2.circle(image, (320, 320), 310, colors['black'], 8)
Наконец, нарисуйте текст внутри часов, чтобы персонализировать их:
cv2.rectangle(image, (150, 175), (490, 270), colors['dark_gray'], -1)
cv2.putText(image, "Mastering OpenCV 4", (150, 200), 1, 2, colors['light_gray'], 1, cv2.LINE_AA)
cv2.putText(image, "with Python", (210, 250), 1, 2, colors['light_gray'], 1, cv2.LINE_AA)
Как только эта статическая информация нарисована на изображении, мы копируем ее в изображение image_original:
image_original = image.copy()
На изображении ниже вы можете увидеть, как выглядят аналоговые часы:
Вычислить часовые тики в массивах hours_orig и hours_dest
Чтобы рассчитать шкалу часовой стрелкиhours_orig
иhours_dest
массив, мы пишемclock_hours.py
рассчитатьhours_orig
иhours_dest
Фиксированные координаты массива. Для вычисления координат (x, y) часовой шкалы используем параметрическое уравнение для окружности:
Рассчитано по приведенной выше формуле, каждые 30 градусов от 0 градусов - это шкала часовой стрелки, всего 12 пунктов.P(x, y)
координата(0
,30
,60
,90
,120
,150
,180
,210
,240
,270
,300
и330
), чтобы получить координаты двух конечных точек, у нас есть два разных радиуса. Таким образом, мы можем получить координаты деления часовой стрелки:
radius = 300
center = (320, 320)
for x in (0, 30, 60, 90, 120, 150, 180, 210, 240, 270, 300, 330):
x_coordinate = center[0] + radius * math.cos(x * 3.14 / 180)
y_coordinate = center[1] + radius * math.sin(x * 3.14 / 180)
print("x: {} y: {}".format(round(x_coordinate), round(y_coordinate)))
print("----------------------")
for x in (0, 30, 60, 90, 120, 150, 180, 210, 240, 270, 300, 330):
x_coordinate = center[0] + (radius - 20) * math.cos(x * 3.14 / 180)
y_coordinate = center[1] + (radius - 20) * math.sin(x * 3.14 / 180)
print("x: {} y: {}".format(round(x_coordinate), round(y_coordinate)))
Отображение текущего времени с помощью аналоговых часов
Когда у вас появится внешний вид циферблата, следующим шагом будет использование аналоговых часов для отображения текущего времени:
- Получить часы, минуты и секунды из текущего времени:
date_time_now = datetime.datetime.now() time_now = date_time_now.time() hour = math.fmod(time_now.hour, 12) minute = time_now.minute second = time_now.second
- Преобразование часов, минут и секунд в градусы для следующего сегмента указателя:
second_angle = math.fmod(second * 6 + 270, 360) minute_angle = math.fmod(minute * 6 + 270, 360) hour_angle = math.fmod((hour*30) + (minute/2) + 270, 360)
- Нарисуйте отрезки, соответствующие часовой, минутной и секундной стрелкам:
second_x = round(320 + 310 * math.cos(second_angle * 3.14 / 180)) second_y = round(320 + 310 * math.sin(second_angle * 3.14 / 180)) cv2.line(image, (320, 320), (second_x, second_y), colors['cyan'], 2) minute_x = round(320 + 260 * math.cos(minute_angle * 3.14 / 180)) minute_y = round(320 + 260 * math.sin(minute_angle * 3.14 / 180)) cv2.line(image, (320, 320), (minute_x, minute_y), colors['cyan'], 8) hour_x = round(320 + 220 * math.cos(hour_angle * 3.14 / 180)) hour_y = round(320 + 220 * math.sin(hour_angle * 3.14 / 180)) cv2.line(image, (320, 320), (hour_x, hour_y), colors['cyan'], 10)
- Наконец, нарисуйте маленький круг в качестве точки соединения трех указателей:
cv2.circle(image, (320, 320), 10, colors['dark_gray'], -1)
Запустив код, вы увидите, что нарисованные аналоговые часы могут корректно отображать текущее время: