//------------------------------------------------------------------------------------------
//
// Title: modelSimplifiedCells.hoc
// Author: Ronald van Elburg (RonaldAJ at vanElburg eu)
//
// Affiliation:
// Department of Artificial Intelligence
// Groningen University
//
// NEURON model specification for the paper:
//
// Ronald A.J. van Elburg and Arjen van Ooyen (2010) `Impact of dendritic size and
// dendritic topology on burst firing in pyramidal cells',
// PLoS Comput Biol 6(5): e1000781. doi:10.1371/journal.pcbi.1000781.
//
// Please consult Readme.txt or instructions on the usage of this file.
//
// This software is released under the GNU GPL version 3:
// http://www.gnu.org/copyleft/gpl.html
//
// The modelcode was partially derived from the code for:
//
// Z. F. Mainen and T. J. Sejnowski (1996) Influence of dendritic
// structure on firing pattern in model neocortical neurons.
// Nature 382: 363-366.
//
// Available from http://senselab.med.yale.edu/ModelDB , accession number 2488
//
//
load_file("nrngui.hoc")
isDefined=name_declared("cad")
if(isDefined!=1){
nrn_load_dll("nrnmech.dll")
}
//Variables for Debugging
MessageLevel=1
strdef procName
// Topology related imports and variables
load_file("hoc/topology.hoc")
load_file("hoc/mep.hoc")
load_file("hoc/LTree.hoc")
objref ClsTop
ClsTop=new ClassTopology()
// To parse strings we need the stringfunctions
objref strfunc
strfunc = new StringFunctions()
// Activate variable timestep method
objref CV_Ode
create cvode_dummy
cvode_dummy {
CV_Ode= new CVode()
CV_Ode.active(1)
L=0.01
diam=0.01
}
// Creation of Sections
create dend[1], soma
// Variables for init(), advance(), connect Stim
// Morphology
noOfTerms=8 // Number of Endsegments
totalDendriticLength=1500 // Total length of the dendritic sections
somaLength=14 // Lengths of the some
terminalDiameter=0.7 // Diameter of the terminal segments
useRall=1 // 1 Use Rall's law, 0 don't use Rall's law
rallPower=3/2 // Rall Power
bconstantSurface=0 // 1 modify TermDiameter to make surface constant, 0 use terminalDiameter
currentTopologyNo=1 // Set asymetric tree as default current topology
// NSeg related settings
dendNSegLength=50 // Maximal segment length of dendritic segments
somaNSeg=1 // Number of segments of axo-somatic section
// Stimuli
bStimSoma=1 //Stimulate dendrites=0 , stimulate soma=1
synapsesPerSection=40 // number synapses per segment
synapseStrength=0.0024 // Bernander 1994
meanInterval=1000 // milliseconds
clampCurrent=0.03 // Strength of stimulus on Soma
// Ion Channels
bActiveDendrites=1 // 1=active, 0=passive
ra_ = 80 // Axial Resistance
//------------------------------------------------------------------------------------------
// Procedure: GenerateMessage(int MessageLevel, string MessageA, string MessageB)
//------------------------------------------------------------------------------------------
proc GenerateMessage(){
if($1==1 && $1<=MessageLevel){
fprint("Entering procedure: %d, %s %s \n", $1 , $s2, $s3)
}else{
if($1<=MessageLevel){
fprint("Message Level: %d, %s %s \n", $1 , $s2, $s3)
}
}
}
//------------------------------------------------------------------------------------------
//Procedure: CellAssemble(int NoOfEndTerminals, int TopologyNumber)
//Description:
// Gets topology numbered with TopologyNumber from the ClassTopology
// and uses this to build a dendritic tree with the corresponding
// topology. The numbering is from fully asymetrical (TopologyNumber = 0)
// to maximal symmetrical (TopologyNumber = NumberOfTopologies-1
// = 2*NoOfEdndTerminals - 2).
//------------------------------------------------------------------------------------------
// Global variables and defaults for CellAssemble procedure
strdef topologyString, copyTopStr, copyTopStr2
strdef tmpMessageStr
rawDiameter=0
proc CellAssemble(){local curDepth,noOfTerms,currentSection,rootSection,useRall,topologyNo, surfaceFactor, constantSurface,RawSurface,rawDiameter localobj rootvec
procName="CellAssemble"
currentSection=0
rootSection=0
noOfTerms=$1
topologyNo=$2
terminalDiameter=$3
useRall=$4
rallPower=$5
constantSurface=$6
forsec "dend" {
disconnect()
uninsert pas
uninsert ca
uninsert cad
uninsert kca
uninsert na
uninsert km
}
// Get the topologystring from the dedicated ClassTopology
ClsTop.GetTopology( topologyString,noOfTerms,topologyNo)
GenerateMessage(1,procName, topologyString)
// Calculate the surface factor= (Surface constant diameter )/(surface Rall power tree)
sprint(copyTopStr2,"%s", topologyString)
surfaceFactor=1
if(constantSurface==1&& useRall==1){
sprint(copyTopStr,"%s", topologyString)
RawSurface=0
while(strfunc.len( copyTopStr)>1){
if(sscanf( copyTopStr,"(%s", copyTopStr)==1){
}else if(sscanf( copyTopStr,")%s", copyTopStr)==1){
}else if(sscanf( copyTopStr,",%s", copyTopStr)==1){
}else{
sscanf( copyTopStr,"%d%s", &rawDiameter, copyTopStr)
RawSurface+=rawDiameter^(1/rallPower)
}
}
surfaceFactor=(2*noOfTerms-1)/RawSurface
}
// Create and initialize the vector keeping track of
// the root of the currently created dendrite segments
rootvec=new Vector(noOfTerms,-1)
curDepth=0
while(strfunc.len( topologyString)>1){
if(sscanf( topologyString,"(%s", topologyString)==1){
curDepth+=1
}else if(sscanf( topologyString,")%s", topologyString)==1){
curDepth-=1
}else if(sscanf( topologyString,",%s", topologyString)==1){
curDepth+=0
}else{
sscanf( topologyString,"%d%s", &rawDiameter, topologyString)
rootvec.x[curDepth]=currentSection
rootSection=rootvec.x[curDepth-1]
if(curDepth >=1){
connect dend[currentSection](0),dend[rootSection](1)
sprint(tmpMessageStr,"connecting: %d with root %d",currentSection,rootSection)
GenerateMessage(2,procName, tmpMessageStr)
}
if(useRall==1){
dend[currentSection].diam=terminalDiameter*surfaceFactor* rawDiameter^(1/rallPower)
}else{
dend[currentSection].diam=terminalDiameter
}
currentSection+=1
}
}
if(noOfTerms==1){
dend[currentSection].diam=terminalDiameter
}
connect dend[0](0), soma(1)
access soma
sprint(topologyString,"%s",copyTopStr2 )
}
//------------------------------------------------------------------------------------------
// Adding constant current stimulus to the soma
//------------------------------------------------------------------------------------------
objref somaStimulus
proc connectSomaStimulus(){
procName="connectSomaStimulus"
GenerateMessage(1,procName,"")
access soma
somaStimulus = new IClamp(0.5)
somaStimulus.loc(0.5)
somaStimulus.amp = clampCurrent
somaStimulus.del = 500
somaStimulus.dur = tstop-somaStimulus.del
}
// Dendritic Stimulation
objref KSyn, KSynList
proc createSynapses(){
procName="createSynapses"
GenerateMessage(1,procName,"")
objref KSyn, KSynList
KSynList=new List()
forsec "dend" {
//L_total+=L
for (x,0) {
KSyn= new SynAlphaPoisson(x)
//total_area+=area(x)
KSyn.mean=meanInterval*nseg/synapsesPerSection
KSyn.tau=0.5
KSyn.offset=tstop-0.1
KSyn.onset=500
KSyn.stim=synapseStrength
KSynList.append(KSyn)
}
}
}
// Setting lengths of the dendritic sections
proc setLengths(){
procName="setLengths"
GenerateMessage(1,procName,"")
forsec "dend" {L=$1}
soma.L=$2
soma.diam=$2
}
//------------------------------------------------------------------------------------------
// Setting the segmentation of the dendritic section and the soma
//------------------------------------------------------------------------------------------
proc setSegmentation() {
procName="setSegmentation"
GenerateMessage(1,procName,"")
forsec "dend" { nseg = int(L/$1+1) }
soma { nseg = $2 }
}
//------------------------------------------------------------------------------------------
//Procedure: equipCells()
//
//History:
//Adjusted copy from the equipCell procedure used by Jacob Duijnhouwer
//
//Description:
//The membrane property values are as in Mainen and Sejnowski's (1996)
//two compartment model. Except the axosomatic channel density which is chosen
//to be 10 times less dense.
//------------------------------------------------------------------------------------------
proc equipCells(){local bActiveDendrites
procName="equipCells"
GenerateMessage(1,procName,"")
bActiveDendrites=$1
if(bActiveDendrites==1){
print "Set Active"
}
// passive properties dendrites
forsec "dend" {
Ra=ra_ //Axial resistivity (ohm cm )
cm=0.75 //membrane capacity (uF-cm^(-2))
insert pas
g_pas = 3.333e-05 // leak conductance=1/(membrane resistivity ) ohm^(1)-cm^(-2)
e_pas = -70 // resting membrane potential
if(bActiveDendrites==1){
// active properties dendrites
insert ca
gbar_ca = 0.3 // high voltage-activatred Ca++
insert cad
insert kca
gbar_kca = 3 // slow Ca++ activated K+
insert na
gbar_na = 15 // fast Na+
insert km
gbar_km = 0.1 // slow voltage dependent non-inactivating K+
ek = -90 //K+ current reversal potential (mV)
ena = 60 //Na+ current reversal potential (mV)
eca = 140 //Ca++ current reversal potential (mV)
ion_style( "ca_ion",0,1,0,0,0) //ion style see section 2.2.3 of Jacob's documentation
}
}
//active conductances, reversal potentials and axial resitivity for soma
forsec "soma" {
Ra=ra_ //Axial resistivity (ohm cm )
cm=0.75 //membrane capacity (uF-cm^(-2))
//Ion Channels
insert kv
gbar_kv = 150 //fast non-inactivating K+ Axo-somatic conductance densitity (pS um^(-2))
insert na
gbar_na = 3000 //fast Na+ Axo-somatic conductance densitity (pS um^(-2))
//current reversal potentials (mV)
ek = -90 //K+
ena = 60 //Na+
}
//passive properties
forall {
global_ra=150 //Spruston and Stuart (1996)
celsius = 37
v_init=-70 //resting membrane potential mV
}
access soma
}
proc customModifications(){
}
proc MRC_PrepareModel(){local sectionLength
procName="MRC_PrepareModel"
GenerateMessage(1,procName,"")
create dend[2*noOfTerms-1]
create soma
sectionLength=totalDendriticLength/(2*noOfTerms-1)
setLengths(sectionLength,somaLength)
setSegmentation(dendNSegLength,somaNSeg)
CellAssemble(noOfTerms,currentTopologyNo,terminalDiameter,useRall,rallPower,bconstantSurface)
if(bStimSoma==0){
createSynapses()
}else{
connectSomaStimulus()
}
equipCells(bActiveDendrites)
customModifications()
}
bStimSoma=0
MRC_PrepareModel()