예제 #1
0
void CInstrumentEditDlg::OnPaint()
{
	CPaintDC dc(this); // device context for painting
	// Do not call CDialog::OnPaint() for painting messages

	const int WHITE_KEY_W	= 10;
	const int BLACK_KEY_W	= 8;

	CBitmap Bmp, WhiteKeyBmp, BlackKeyBmp, WhiteKeyMarkBmp, BlackKeyMarkBmp;
	Bmp.CreateCompatibleBitmap(&dc, 800, 800);
	WhiteKeyBmp.LoadBitmap(IDB_KEY_WHITE);
	BlackKeyBmp.LoadBitmap(IDB_KEY_BLACK);
	WhiteKeyMarkBmp.LoadBitmap(IDB_KEY_WHITE_MARK);
	BlackKeyMarkBmp.LoadBitmap(IDB_KEY_BLACK_MARK);

	CDC BackDC;
	BackDC.CreateCompatibleDC(&dc);
	CDCObjectContext c {BackDC, &Bmp};		// // //

	CDC WhiteKey;
	WhiteKey.CreateCompatibleDC(&dc);
	CDCObjectContext c2 {WhiteKey, &WhiteKeyBmp};		// // //

	CDC BlackKey;
	BlackKey.CreateCompatibleDC(&dc);
	CDCObjectContext c3 {BlackKey, &BlackKeyBmp};		// // //
	
	const int WHITE[]	= {NOTE_C, NOTE_D, NOTE_E, NOTE_F, NOTE_G, NOTE_A, NOTE_B};
	const int BLACK_1[] = {NOTE_Cs, NOTE_Ds};
	const int BLACK_2[] = {NOTE_Fs, NOTE_Gs, NOTE_As};

	int Note = GET_NOTE(m_iActiveKey);		// // //
	int Octave = GET_OCTAVE(m_iActiveKey);

	for (int j = 0; j < 8; j++) {
		int Pos = (WHITE_KEY_W * 7) * j;

		for (int i = 0; i < 7; i++) {
			bool Selected = (Note == WHITE[i]) && (Octave == j) && m_iActiveKey != -1;
			WhiteKey.SelectObject(Selected ? WhiteKeyMarkBmp : WhiteKeyBmp);
			int Offset = i * WHITE_KEY_W;
			BackDC.BitBlt(Pos + Offset, 0, 100, 100, &WhiteKey, 0, 0, SRCCOPY);
		}

		for (int i = 0; i < 2; i++) {
			bool Selected = (Note == BLACK_1[i]) && (Octave == j) && m_iActiveKey != -1;
			BlackKey.SelectObject(Selected ? BlackKeyMarkBmp : BlackKeyBmp);
			int Offset = i * WHITE_KEY_W + WHITE_KEY_W / 2 + 1;
			BackDC.BitBlt(Pos + Offset, 0, 100, 100, &BlackKey, 0, 0, SRCCOPY);
		}

		for (int i = 0; i < 3; i++) {
			bool Selected = (Note == BLACK_2[i]) && (Octave == j) && m_iActiveKey != -1;
			BlackKey.SelectObject(Selected ? BlackKeyMarkBmp : BlackKeyBmp);
			int Offset = (i + 3) * WHITE_KEY_W + WHITE_KEY_W / 2 + 1;
			BackDC.BitBlt(Pos + Offset, 0, 100, 100, &BlackKey, 0, 0, SRCCOPY);
		}
	}

	dc.BitBlt(m_KeyboardRect.left, m_KeyboardRect.top, KEYBOARD_WIDTH, KEYBOARD_HEIGHT, &BackDC, 0, 0, SRCCOPY);		// // //
}
예제 #2
0
파일: piano.c 프로젝트: eriser/Synth
int main() {
    uint8_t i, id;
    uint8_t timing[19]; // This controller control 18 keys
    uint8_t cnt[19]; // This controller control 18 keys
    uint32_t status[19]; // This controller control 18 keys
    
    // program setup
    discharge_ports();
    SREG = 0; // No interrupts
    
    DDRD |= _BV(PIND0); // NOTE: Only output pin is number 0
    PORTD0_SBI;

    for (i = 0; i < 19; i++) {
        timing[i] = 0;
        cnt[i]    = 0;
        status[i] = 0;
    }
    
    // main loop
    while(1) {
        // first step: check wether a key was pressed or not
        for (i = 0; i < 19; i++) {
            id = i + 1;
            if (check_port(id)) {
                if (!(status[i] & 0x80000000L)) // wasting a 0
                    cnt[i]++; // added one 1
                // else // wasting 1, cnt does not change
                status[i] <<= 1; // shift
                status[i] |= 1; // last added is 1
                
                if (cnt[i] > THRESHOLD) {
                    if (timing[i]) // key was already pressed
                        timing[i] = SUST;
                    else
                        timing[i] = SUST + 1;
                }
            } else {
                if (status[i] & 0x80000000L) // wasting a 1
                    cnt[i]--; // removed one 1
                // else // wasting 1, cnt does not change
                status[i] <<= 1; // shift, last byte is already 1
                
                if (timing[i])
                    timing[i]--;
            }
        }
        
        discharge_ports(); // after reading discharges ports for the next reading
        
        // second step: if some messages are true then send data to the synth
        for (i = 0; i < 19; i++)
            if (timing[i] == SUST + 1) {
                send_message(0x80 | GET_NOTE(i));
            } else if (timing[i] == 1) {
                send_message(0x00 | GET_NOTE(i));
            }

        //_delay_us(100); // wait some time
    }
    
    return 0;
}