Interrupt and PWM conflict (DC Motor & wheel encoder)

Hi there everyone!!!
I use an Arduino Mega to do these 2 things
1.Driving a DC 24V Motor via a Power-Mosfet H-bridge and controling speed and direction via analogWrite [PWM]&digitalWrite.

2.Feedback the motor’s position via a Wheel Disk and photointerrupter,reading the photointerrupter’s signal RISING as a attachInterrupt ISR.

the 24VDC H-bridge is like this

ABCD pins inside the above image , is process by two logic IC ,XOR&AND ,
to use only two pins to control the motor(Forward/Backward/Stop/Brake).

the photointerrupter encoder and wheel disk are like this

the encoder signal connect to pin 20 (intterupt 4 in MEGA)

void setup(){
  Serial.begin(9600);
  attachInterrupt(4, change_encoder, RISING);
}

change_encoder() is the ISR function to accumulate the encoder’s value

volatile int  encoder,encoder_last;
void change_encoder(){
  encoder++;
}

Then I print out the encoder’s value using serial port,
and control the motor using analogWrite&digitalWrite

void loop(){
 if(encoder!=encoder_last) //print only when encoder change
   Serial<<encoder<<endl;
 encolder_last=encoder; 

 analogWrite(4,50);
 digitalWrite(5,LOW);
}

pin4&5 are the control pins of H-bridge.
if i change the ‘1’'s code from digitalWrite(4/5,HIGH) to analogWrite(4,5,0-255)
it will be the PWM speed control of Motor
pin4 pin5
1 0 Forward
0 1 Backward
0 0 Stop
1 1 Brake

NOW here comes the problem!!!
when I use digitalWrite with both motor control pins (motor full speed)

 digitalWrite(4,HIGH);
 digitalWrite(5,LOW);

the encoder works well like this(serial monitor)
1->2->3->4->5->6…
everytime encoder moves one step , encoder acc one

but when i use analogWrite with motor contorl pins (motor PWM speed)

analogWrite(4,50);
digitalWrite(5,LOW)

1->4->7->8->9->10->11->12->14->16…
everytime encoder moves one step, encoder acc unstable
maybe 1 jump to 11 12 jump to 16 everystep

I dont know if it is the electronic problem or programming problem.
hope some one can help!!

You H-bridge is flawed. You need to drive A, B, C and D directly, not via that logic circuit - its absolutely vital that you switch off one arm of the H-bridge before switching on the other - that circuit is very slow to switch off the upper p-FETs and the way you have it the 24V supply will be shorted out on every transition for perhaps 2 to 5 us - this could easily blow up the MOSFETs and will certainly cause massive current spikes that will interfer with circuit operation.

The p-channel FETs you have specify a total gate charge of 53nC, and you are charging/discharging them through 2 1k resistors (effectively in parallel). Thus a maximum of 24 mA is available (12V / 500 ohms) to charge/discharge that 53nC, the fastest it can be done is thus 2.2us, in practice most of the charge has to be drained when the gate is at -4V or so (8mA available) so more like 5us is needed. If you simultaneously switch on the low-side nchannel FET it is likely to switch on much sooner, and you have two FETs switched on across a 24V battery (capable of > 200A perhaps?).

You need to read up on "shoot-through" in H-bridges. By switching each FET individually you can avoid this situation by including suitable delays. If you want to drive from a single PWM line you'll need to develop a delay circuit to implement the delays. Hint available H-bridge driver chips usually provide adjustable delays and can also switch MOSFETs much faster (gate drive impedance a lot lower than 500 ohms).