// sketch.ino
// Curve Tracer (NPN/PNP) - Arduino Nano (Wokwi). Datum: 2025-10-07
// Pins anpassen an diagram.json Layout
const int pwmIbPin = 3; // PWM -> Basisstromquelle (über OpAmp)
const int pwmVcePin = 5; // PWM -> VCE (über OpAmp)
const int enPin = 4; // Enable (optional)
const int senseIcPin = A0; // Shunt Kollektor
const int senseIbPin = A1; // Shunt Basis
const int senseVcePin = A2;// VCE Messung
// Hardware-Parameter (kalibrieren in deiner Schaltung)
const float RshuntC = 10.0; // Ohm (Beispiel)
const float RshuntB = 1000.0; // Ohm (Beispiel)
const float adcRef = 5.0;
const int adcSamples = 40;
const int pwmMax = 255;
void setup(){
Serial.begin(115200);
pinMode(pwmIbPin, OUTPUT);
pinMode(pwmVcePin, OUTPUT);
pinMode(enPin, OUTPUT);
analogWrite(pwmIbPin, 0);
analogWrite(pwmVcePin, 0);
digitalWrite(enPin, HIGH);
delay(200);
Serial.println("CurveTracer ready (I_CE0, HFE, KENN)");
}
long readAdcAveraged(int pin, int samples){
long sum = 0;
for(int i=0;i<samples;i++){
sum += analogRead(pin);
delayMicroseconds(500);
}
return sum / samples;
}
float readVoltage(int pin){
long v = readAdcAveraged(pin, adcSamples);
return (v * adcRef) / 1023.0;
}
void setPwm(int pin,int val){
val = constrain(val,0,pwmMax);
analogWrite(pin,val);
}
float measureIc_mA(){
float v = readVoltage(senseIcPin);
float ic = v / RshuntC;
return ic * 1000.0;
}
float measureIb_uA(){
float v = readVoltage(senseIbPin);
float ib = v / RshuntB;
return ib * 1e6;
}
float measureVce_V(){
return readVoltage(senseVcePin);
}
void cmd_I_CE0(){
setPwm(pwmIbPin,0);
delay(150);
setPwm(pwmVcePin,pwmMax);
delay(250);
float ic = measureIc_mA();
Serial.print("I_CE0_mA,"); Serial.println(ic,6);
setPwm(pwmVcePin,0);
}
void cmd_HFE(){
float IbTargets_uA[] = {10.0,50.0,100.0,200.0};
int n = sizeof(IbTargets_uA)/sizeof(float);
Serial.println("Ib_uA,Ic_mA,hFE,Vce_V");
for(int i=0;i<n;i++){
float t = IbTargets_uA[i];
int pwm = (int)constrain((t/200.0)*pwmMax,0,pwmMax);
setPwm(pwmIbPin,pwm);
setPwm(pwmVcePin,pwmMax);
delay(200);
float ib = measureIb_uA();
float ic = measureIc_mA();
float hfe = (ib > 0.5) ? ( (ic/1000.0) / (ib/1e6) ) : 0.0;
float vce = measureVce_V();
Serial.print(ib,3); Serial.print(",");
Serial.print(ic,6); Serial.print(",");
Serial.print(hfe,3); Serial.print(",");
Serial.println(vce,3);
delay(150);
}
setPwm(pwmIbPin,0);
setPwm(pwmVcePin,0);
}
void cmd_KENN(){
float IbStages_uA[] = {10.0,50.0,100.0};
int nIb = sizeof(IbStages_uA)/sizeof(float);
int steps = 20;
Serial.println("Ib_uA,Vce_V,Ic_mA");
for(int j=0;j<nIb;j++){
float target = IbStages_uA[j];
int pwmIb = (int)constrain((target/200.0)*pwmMax,0,pwmMax);
setPwm(pwmIbPin,pwmIb);
delay(120);
for(int s=0;s<=steps;s++){
float frac = (float)s/steps;
setPwm(pwmVcePin,(int)(frac*pwmMax));
delay(80);
float vce = measureVce_V();
float ic = measureIc_mA();
Serial.print(target,3); Serial.print(",");
Serial.print(vce,3); Serial.print(",");
Serial.println(ic,6);
}
delay(120);
}
setPwm(pwmIbPin,0);
setPwm(pwmVcePin,0);
}
String buf="";
void loop(){
while(Serial.available()){
char c = Serial.read();
if(c=='\n' || c=='\r'){
String cmd = buf;
cmd.trim();
if(cmd.equalsIgnoreCase("I_CE0")) cmd_I_CE0();
else if(cmd.equalsIgnoreCase("HFE")) cmd_HFE();
else if(cmd.equalsIgnoreCase("KENN")) cmd_KENN();
else Serial.println("Unknown");
buf="";
} else buf += c;
}
}