Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: Вывод переменной из AVR на принтер
Форум разработчиков электроники ELECTRONIX.ru > Сайт и форум > В помощь начинающему > MCS51, AVR, PIC, STM8, 8bit
Graf83
Подскажите пожалуйста как вывести переменную на печать, программирую в codevision.
Может есть уже готовый кусок программы? Принтер буду использовать EPSON LX300+ или термопринтер
rezident
Сразу видно, что вопрос формулировал новичок rolleyes.gif
Переменная какого типа предназначена для вывода? Целочисленную переменную перевести в символьный вид будет проще, чем, например, float.
Через какой интерфейс нужно вывести: CENTRONICS или RS-232?
Вывести на принтер нужно абы как или сформировать строку определенного вида/оформления? С системой команд/управляющими кодами принтера EPSON вы уже ознакомились?
nk@
Цитата(Graf83 @ Apr 5 2011, 16:20) *
программирую в codevision.
Может есть уже готовый кусок программы?

Исходных данных маловато.
1. На чем пишем (С или ASM)?
2. Вам нужен драйвер. Отсюда возникает вопрос, сформулированный rezident: Тип физичесчкого интерфейса?
3. На каком чипе хотите сделать? Centronics, например, требует минимум 10 линий (8 - data, strobe, busy)

PS:У меня есть решение для Centronics на С, правда под GCC. Драйвер с FIFO, и потом, обычным printf-ом, печатайте в свое удовольствие sm.gif
hd44780
Цитата(nk@ @ Apr 5 2011, 20:00) *
1. На чем пишем (С или ASM)?

Он сказал - CodeVision. Значит - С.

Цитата(nk@ @ Apr 5 2011, 20:00) *
Тип физичесчкого интерфейса?

USB w00t.gif . Действительно, они там разные есть ... Только что гуглом смотрел.

Цитата(nk@ @ Apr 5 2011, 20:00) *
минимум 10 линий (8 - data, strobe, busy)


+1 - PaperOut - бумагу проверять. И Ack надо бы ...

Поищите древнюю книжку Р. Джордейн "Аппаратные средства IBM PC/XT".
Там все есть. Для LPT порта (Cetronics).
Правда, в расчете на 8086/8088 проц и MSDOS, но это ж не проблема biggrin.gif .
vvs157
Цитата(hd44780 @ Apr 6 2011, 12:45) *
USB w00t.gif . Действительно, они там разные есть ...
Какой USB у старого матричного принтера? EPSON LX300+ только Centronix и RS-232.
hd44780
Цитата(vvs157 @ Apr 6 2011, 10:51) *
Какой USB у старого матричного принтера?

Ну пошутил я biggrin.gif .

Цитата(vvs157 @ Apr 6 2011, 10:51) *
EPSON LX300+ только Centronix. Возможно были очень экзотические модели с RS-232.

Я лично никогда не видел никаких принтеров на COM порт. Старые - LPT, новые - USB. Правда, они уже не матричные.

Кстати - http://old.epson.ru/products/printers/dotm...&print=true
Есть и USB. Так что зря вы смеетесь.
Graf83
переменная типа int или char, интерфейс lpt (cetronics) пишу на си

систему команд на принтер я смотрел, для меня пока это очень сложно, может пример у кого-то есть вывода информации на принтер (lpt)

чип atmega162
nk@
Цитата(Graf83 @ Apr 6 2011, 12:17) *
переменная типа int или char, интерфейс lpt (cetronics) пишу на си
чип atmega162

Вот Вам готовый код, выкусил из старого проекта (печатался протокол измерений, работает у людей до сих пор sm.gif).
Собиралось на меге16, компилятор GCC (WinAVR). Хотите под CV - портируйте.
Особенности:
-использует аппаратные прерывания для сигналов BUSY и ACK.
-циклический буфер (FIFO)
Не забудьте линию SELECT_IN подключить к 0, и линию AUTO_FEED к питанию (лог 1)
Рекомендую подключить линии принтера через резисторы 50-100 ом.
Если линии прерывания заняты под другие цели, то можно и без них обойтись - уберите #define USE_INTERRUPTS и в каком - либо цикле или в таймере запускайте периодически LPT_BSR()

Печатать можно (как Вы уже заметили в main()) обычным printf() все, что пожелаете sm.gif Или используйте LPT_putc() напрямую, если нужно.

CODE
#include <avr/io.h>
#include <string.h>
#include <stdio.h>
#include <util/delay.h>
#include <stdlib.h>
#include <avr/interrupt.h>

#define USE_INTERRUPTS

#define DATA_PORT PORTC // DO..D7 принтера
#define DATA_DDR DDRC

#define STATE_PORT PORTD // линии управления принтера
#define STATE_PIN PIND
#define STATE_DDR DDRD

#define BUSY_PIN 2 //INT0
#define ACK_PIN 3 //INT1

#define PAPER_OUT_PIN 4
#define ERROR_PIN 5
#define INIT_PIN 6
#define STROBE_PIN 7

#ifndef BUFFER_SIZE
#define BUFFER_SIZE 32
#endif

#define BUFFER_MASK ( BUFFER_SIZE - 1)

#if ( BUFFER_SIZE & BUFFER_MASK )
#error Buffer size is not a power of 2
#endif

volatile uint8_t Buf[BUFFER_SIZE];
volatile uint8_t Head;
volatile uint8_t Tail;
volatile uint8_t printer_state = 0;

void LPT_init(void)
{
DATA_DDR = 0xFF;
STATE_PORT |= (1<<INIT_PIN) | (1<<STROBE_PIN);
STATE_DDR |= (1<<INIT_PIN) | (1<<STROBE_PIN); //Output pins
STATE_DDR &= ~((1<<BUSY_PIN) | (1<<ACK_PIN) | (1<<PAPER_OUT_PIN) | (1<<ERROR_PIN)); //Input pins
Head = 0;
Tail = 0;
#ifdef USE_INTERRUPTS
MCUCR = (1<<ISC01) | (1<ISC11); //interrupts on falling edge
GICR |= (1<<INT0) | (1<<INT1);
sei();
#endif
}

void init_printer(void)
{
STATE_PORT &= ~(1<<INIT_PIN);
_delay_us(5);
STATE_PORT &= ~(1<<INIT_PIN);
_delay_us(100);
}

uint8_t LPT_state(void)
{
uint8_t state = 0;
if(STATE_PIN & (1<<BUSY_PIN)) state |= 1; //Printer busy
if(STATE_PIN & (1<<PAPER_OUT_PIN)) state |= 2; //Paper out
if(!(STATE_PIN & (1<<ERROR_PIN))) state |= 4; //Internal printer error
return state;
}

uint8_t LPT_transmit(void)
{
uint8_t tmp;

if(Head == Tail) return 0; //Buffer empty, nothing to send
printer_state = LPT_state(); if(printer_state) return printer_state; // printer not redy
tmp = (Tail + 1) & BUFFER_MASK; // calculate and store new buffer index
Tail = tmp;
DATA_PORT = Buf[tmp]; // get one byte from buffer and write it to out port
// do STROBE pulse
_delay_us(1);
STATE_PORT &= ~(1<<STROBE_PIN);
_delay_us(1);
STATE_PORT |= (1<<STROBE_PIN);
_delay_us(1);
return 0; //succes
}

void LPT_BSR(void)
{
do
{
printer_state = LPT_transmit();
} while((printer_state==0)&&(Head!=Tail)); //try transmission
}


#ifdef USE_INTERRUPTS

ISR(INT0_vect)
{
//Busy signal go down, wakeup
LPT_BSR();
}

ISR(INT1_vect)
{
//ACK signal arrived
LPT_BSR();
}

#endif

void LPT_putc(unsigned char data)
{
uint8_t tmp;

tmp = (Head + 1) & BUFFER_MASK;

while ( tmp == Tail ){
;// wait for free space in buffer
}

Buf[tmp] = data;
Head = tmp;
LPT_BSR();
}



static int lpt_putchar(char c, FILE *stream)
{
if (c == '\n') LPT_putc('\r'); // insert CR before LF
LPT_putc(с);
return 0;
}

FILE lptf = FDEV_SETUP_STREAM(lpt_putchar, NULL, _FDEV_SETUP_WRITE);



int main( void )
{
int test_value = 315;

LPT_init(); // driver init
init_printer(); // необязательно
_delay_ms(1000); // для некоторых старых принтеров может потребоваться задержка после сброса и больше (2-3 секунды), если что, подправьте

stdout = &lptf; // назначаем STDOUT на принтер

printf("Hello printer!\n");
printf("Value = %d\n", test_value);

return 0;
}



PS: Если чео неясно - спрашивайте.
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.